From e088e4c9cdb618675874becb91b2fd581ee707e6 Mon Sep 17 00:00:00 2001 From: Matthew Garrett Date: Tue, 25 Nov 2008 13:29:47 -0500 Subject: [CPUFREQ] Disable sysfs ui for p4-clockmod. p4-clockmod has a long history of abuse. It pretends to be a CPU frequency scaling driver, even though it doesn't actually change the CPU frequency, but instead just modulates the frequency with wait-states. The biggest misconception is that when running at the lower 'frequency' p4-clockmod is saving power. This isn't the case, as workloads running slower take longer to complete, preventing the CPU from entering deep C states. However p4-clockmod does have a purpose. It can prevent overheating. Having it hooked up to the cpufreq interfaces is the wrong way to achieve cooling however. It should instead be hooked up to ACPI. This diff introduces a means for a cpufreq driver to register with the cpufreq core, but not present a sysfs interface. Signed-off-by: Matthew Garrett Signed-off-by: Dave Jones --- include/linux/cpufreq.h | 1 + 1 file changed, 1 insertion(+) (limited to 'include/linux') diff --git a/include/linux/cpufreq.h b/include/linux/cpufreq.h index 1ee608fd7b77..484b3abf61bb 100644 --- a/include/linux/cpufreq.h +++ b/include/linux/cpufreq.h @@ -234,6 +234,7 @@ struct cpufreq_driver { int (*suspend) (struct cpufreq_policy *policy, pm_message_t pmsg); int (*resume) (struct cpufreq_policy *policy); struct freq_attr **attr; + bool hide_interface; }; /* flags */ -- cgit v1.2.2 From 47fea2adfc9e16846bc57c2f64ff233b354fef39 Mon Sep 17 00:00:00 2001 From: Jaswinder Singh Rajput Date: Mon, 29 Dec 2008 23:39:17 +0530 Subject: sched: sched.c declare variables before they get used Impact: cleanup, avoid sparse warnings In linux/sched.h moved out sysctl_sched_latency, sysctl_sched_min_granularity, sysctl_sched_wakeup_granularity, sysctl_sched_shares_ratelimit and sysctl_sched_shares_thresh from #ifdef CONFIG_SCHED_DEBUG as these variables are common for both. Fixes these sparse warnings: kernel/sched.c:825:14: warning: symbol 'sysctl_sched_shares_ratelimit' was not declared. Should it be static? kernel/sched.c:832:14: warning: symbol 'sysctl_sched_shares_thresh' was not declared. Should it be static? kernel/sched_fair.c:37:14: warning: symbol 'sysctl_sched_latency' was not declared. Should it be static? kernel/sched_fair.c:43:14: warning: symbol 'sysctl_sched_min_granularity' was not declared. Should it be static? kernel/sched_fair.c:72:14: warning: symbol 'sysctl_sched_wakeup_granularity' was not declared. Should it be static? Signed-off-by: Jaswinder Singh Rajput Signed-off-by: Ingo Molnar --- include/linux/sched.h | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) (limited to 'include/linux') diff --git a/include/linux/sched.h b/include/linux/sched.h index 8395e715809d..01d9fd268eb0 100644 --- a/include/linux/sched.h +++ b/include/linux/sched.h @@ -1651,16 +1651,16 @@ extern void wake_up_idle_cpu(int cpu); static inline void wake_up_idle_cpu(int cpu) { } #endif -#ifdef CONFIG_SCHED_DEBUG extern unsigned int sysctl_sched_latency; extern unsigned int sysctl_sched_min_granularity; extern unsigned int sysctl_sched_wakeup_granularity; +extern unsigned int sysctl_sched_shares_ratelimit; +extern unsigned int sysctl_sched_shares_thresh; +#ifdef CONFIG_SCHED_DEBUG extern unsigned int sysctl_sched_child_runs_first; extern unsigned int sysctl_sched_features; extern unsigned int sysctl_sched_migration_cost; extern unsigned int sysctl_sched_nr_migrate; -extern unsigned int sysctl_sched_shares_ratelimit; -extern unsigned int sysctl_sched_shares_thresh; int sched_nr_latency_handler(struct ctl_table *table, int write, struct file *file, void __user *buffer, size_t *length, -- cgit v1.2.2 From 1c5745aa380efb6417b5681104b007c8612fb496 Mon Sep 17 00:00:00 2001 From: Thomas Gleixner Date: Mon, 22 Dec 2008 23:05:28 +0100 Subject: sched_clock: prevent scd->clock from moving backwards, take #2 Redo: 5b7dba4: sched_clock: prevent scd->clock from moving backwards which had to be reverted due to s2ram hangs: ca7e716: Revert "sched_clock: prevent scd->clock from moving backwards" ... this time with resume restoring GTOD later in the sequence taken into account as well. The "timekeeping_suspended" flag is not very nice but we cannot call into GTOD before it has been properly resumed and the scheduler will run very early in the resume sequence. Cc: Signed-off-by: Ingo Molnar --- include/linux/time.h | 1 + 1 file changed, 1 insertion(+) (limited to 'include/linux') diff --git a/include/linux/time.h b/include/linux/time.h index ce321ac5c8f8..fbbd2a1c92ba 100644 --- a/include/linux/time.h +++ b/include/linux/time.h @@ -105,6 +105,7 @@ extern unsigned long read_persistent_clock(void); extern int update_persistent_clock(struct timespec now); extern int no_sync_cmos_clock __read_mostly; void timekeeping_init(void); +extern int timekeeping_suspended; unsigned long get_seconds(void); struct timespec current_kernel_time(void); -- cgit v1.2.2 From 9188e79ec3fd43a0a605274324aecfb731baa88b Mon Sep 17 00:00:00 2001 From: Jiri Kosina Date: Wed, 12 Nov 2008 16:14:08 +0100 Subject: HID: add phys and name ioctls to hidraw The hiddev interface provides ioctl() calls which can be used to obtain phys and raw name of the underlying device. Add the corresponding support also into hidraw. Signed-off-by: Jiri Kosina --- include/linux/hidraw.h | 2 ++ 1 file changed, 2 insertions(+) (limited to 'include/linux') diff --git a/include/linux/hidraw.h b/include/linux/hidraw.h index dbb5c8c374f0..dd8d69269176 100644 --- a/include/linux/hidraw.h +++ b/include/linux/hidraw.h @@ -33,6 +33,8 @@ struct hidraw_devinfo { #define HIDIOCGRDESCSIZE _IOR('H', 0x01, int) #define HIDIOCGRDESC _IOR('H', 0x02, struct hidraw_report_descriptor) #define HIDIOCGRAWINFO _IOR('H', 0x03, struct hidraw_devinfo) +#define HIDIOCGRAWNAME(len) _IOC(_IOC_READ, 'H', 0x04, len) +#define HIDIOCGRAWPHYS(len) _IOC(_IOC_READ, 'H', 0x05, len) #define HIDRAW_FIRST_MINOR 0 #define HIDRAW_MAX_DEVICES 64 -- cgit v1.2.2 From 0ed94b334265b6ee3e3336b4fedacfa9cb2ccaba Mon Sep 17 00:00:00 2001 From: Jiri Slaby Date: Mon, 24 Nov 2008 16:20:07 +0100 Subject: HID: move usbhid flags to usbhid.h Move usbhid specific flags from global hid.h into local usbhid.h. Signed-off-by: Jiri Slaby Signed-off-by: Jiri Kosina --- include/linux/hid.h | 9 --------- 1 file changed, 9 deletions(-) (limited to 'include/linux') diff --git a/include/linux/hid.h b/include/linux/hid.h index e5780f8c934a..2c20f20283b2 100644 --- a/include/linux/hid.h +++ b/include/linux/hid.h @@ -403,15 +403,6 @@ struct hid_output_fifo { #define HID_STAT_ADDED 1 #define HID_STAT_PARSED 2 -#define HID_CTRL_RUNNING 1 -#define HID_OUT_RUNNING 2 -#define HID_IN_RUNNING 3 -#define HID_RESET_PENDING 4 -#define HID_SUSPENDED 5 -#define HID_CLEAR_HALT 6 -#define HID_DISCONNECTED 7 -#define HID_STARTED 8 - struct hid_input { struct list_head list; struct hid_report *report; -- cgit v1.2.2 From 3a6f82f7a22cf19687f556997c6978b31c109360 Mon Sep 17 00:00:00 2001 From: Jiri Slaby Date: Mon, 24 Nov 2008 16:20:09 +0100 Subject: HID: add dynids facility Allow adding new devices to the hid drivers on the fly without a need of kernel recompilation. Now, one can test a driver e.g. by: echo 0003:045E:00F0.0003 > ../generic-usb/unbind echo 0003 045E 00F0 > new_id from some driver subdir. Signed-off-by: Jiri Slaby Signed-off-by: Jiri Kosina --- include/linux/hid.h | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'include/linux') diff --git a/include/linux/hid.h b/include/linux/hid.h index 2c20f20283b2..215035bbb288 100644 --- a/include/linux/hid.h +++ b/include/linux/hid.h @@ -531,6 +531,8 @@ struct hid_usage_id { * @name: driver name (e.g. "Footech_bar-wheel") * @id_table: which devices is this driver for (must be non-NULL for probe * to be called) + * @dyn_list: list of dynamically added device ids + * @dyn_lock: lock protecting @dyn_list * @probe: new device inserted * @remove: device removed (NULL if not a hot-plug capable driver) * @report_table: on which reports to call raw_event (NULL means all) @@ -558,6 +560,9 @@ struct hid_driver { char *name; const struct hid_device_id *id_table; + struct list_head dyn_list; + spinlock_t dyn_lock; + int (*probe)(struct hid_device *dev, const struct hid_device_id *id); void (*remove)(struct hid_device *dev); -- cgit v1.2.2 From 725cf0f47dbb02e0482f081828cff73f55479b79 Mon Sep 17 00:00:00 2001 From: Hannes Eder Date: Tue, 16 Dec 2008 14:20:23 +0100 Subject: HID: avoid sparse warning in HID_COMPAT_LOAD_DRIVER Impact: include a prototype for the exported function in the macro Fix about 20 of this warnings: drivers/hid/hid-a4tech.c:162:1: warning: symbol 'hid_compat_a4tech' was not declared. Should it be static? Signed-off-by: Hannes Eder Signed-off-by: Jiri Kosina --- include/linux/hid.h | 2 ++ 1 file changed, 2 insertions(+) (limited to 'include/linux') diff --git a/include/linux/hid.h b/include/linux/hid.h index 215035bbb288..81aa84d60c6b 100644 --- a/include/linux/hid.h +++ b/include/linux/hid.h @@ -793,6 +793,8 @@ dbg_hid(const char *fmt, ...) #ifdef CONFIG_HID_COMPAT #define HID_COMPAT_LOAD_DRIVER(name) \ +/* prototype to avoid sparse warning */ \ +extern void hid_compat_##name(void); \ void hid_compat_##name(void) { } \ EXPORT_SYMBOL(hid_compat_##name) #else -- cgit v1.2.2 From c66b9906f863696159e05890bb7123269bb9a9de Mon Sep 17 00:00:00 2001 From: Ingo Molnar Date: Sun, 4 Jan 2009 10:55:02 +0100 Subject: intel-iommu: fix build error with INTR_REMAP=y and DMAR=n dmar.o can be built in the CONFIG_INTR_REMAP=y case but iommu_calculate_agaw() is only available if VT-d is built as well. So create an inline version of iommu_calculate_agaw() for the !CONFIG_DMAR case. The iommu->agaw value wont be used in this case, but the code is cleaner (has less #ifdefs) if we have it around unconditionally. Signed-off-by: Ingo Molnar --- include/linux/dma_remapping.h | 8 ++++++++ 1 file changed, 8 insertions(+) (limited to 'include/linux') diff --git a/include/linux/dma_remapping.h b/include/linux/dma_remapping.h index 136f170cecc2..af1dab41674b 100644 --- a/include/linux/dma_remapping.h +++ b/include/linux/dma_remapping.h @@ -17,7 +17,15 @@ struct dmar_domain; struct root_entry; extern void free_dmar_iommu(struct intel_iommu *iommu); + +#ifdef CONFIG_DMAR extern int iommu_calculate_agaw(struct intel_iommu *iommu); +#else +static inline int iommu_calculate_agaw(struct intel_iommu *iommu) +{ + return 0; +} +#endif extern int dmar_disabled; -- cgit v1.2.2 From 0c8a601678960fbcc1c1185a283d6d107575810b Mon Sep 17 00:00:00 2001 From: Mark Brown Date: Sat, 8 Nov 2008 01:10:16 +0100 Subject: mfd: Add WM8350 revision H support No other software changes are required. Signed-off-by: Mark Brown Signed-off-by: Samuel Ortiz --- include/linux/mfd/wm8350/core.h | 1 + 1 file changed, 1 insertion(+) (limited to 'include/linux') diff --git a/include/linux/mfd/wm8350/core.h b/include/linux/mfd/wm8350/core.h index 6ebf97f2a475..9490ec175d5a 100644 --- a/include/linux/mfd/wm8350/core.h +++ b/include/linux/mfd/wm8350/core.h @@ -536,6 +536,7 @@ #define WM8350_REV_E 0x4 #define WM8350_REV_F 0x5 #define WM8350_REV_G 0x6 +#define WM8350_REV_H 0x7 #define WM8350_NUM_IRQ 63 -- cgit v1.2.2 From 67488526349d043372d141c054f4dc6313780b3c Mon Sep 17 00:00:00 2001 From: Mark Brown Date: Sat, 8 Nov 2008 01:10:21 +0100 Subject: mfd: Add AUXADC support for WM8350 The auxiliary ADC in the WM8350 is shared between several subdevices so access to it needs to be arbitrated by the core driver. Signed-off-by: Mark Brown Signed-off-by: Samuel Ortiz --- include/linux/mfd/wm8350/comparator.h | 8 ++++++++ include/linux/mfd/wm8350/core.h | 2 ++ 2 files changed, 10 insertions(+) (limited to 'include/linux') diff --git a/include/linux/mfd/wm8350/comparator.h b/include/linux/mfd/wm8350/comparator.h index 053788649452..54bc5d0fd502 100644 --- a/include/linux/mfd/wm8350/comparator.h +++ b/include/linux/mfd/wm8350/comparator.h @@ -164,4 +164,12 @@ #define WM8350_AUXADC_BATT 6 #define WM8350_AUXADC_TEMP 7 +struct wm8350; + +/* + * AUX ADC Readback + */ +int wm8350_read_auxadc(struct wm8350 *wm8350, int channel, int scale, + int vref); + #endif diff --git a/include/linux/mfd/wm8350/core.h b/include/linux/mfd/wm8350/core.h index 9490ec175d5a..cc190055b9c4 100644 --- a/include/linux/mfd/wm8350/core.h +++ b/include/linux/mfd/wm8350/core.h @@ -573,6 +573,8 @@ struct wm8350 { void *src); u16 *reg_cache; + struct mutex auxadc_mutex; + /* Interrupt handling */ struct work_struct irq_work; struct mutex irq_mutex; /* IRQ table mutex */ -- cgit v1.2.2 From 3fba19ec1ae5b460c73a7f32efed8d3b3300b246 Mon Sep 17 00:00:00 2001 From: David Brownell Date: Sat, 8 Nov 2008 01:13:16 +0100 Subject: mfd: allow reading entire register banks on twl4030 Minor change to the TWL4030 utility interface: support reads of all 256 bytes in each register bank (vs just 255). This can help when debugging, but is otherwise a NOP. Signed-off-by: David Brownell Signed-off-by: Samuel Ortiz --- include/linux/i2c/twl4030.h | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'include/linux') diff --git a/include/linux/i2c/twl4030.h b/include/linux/i2c/twl4030.h index fb604dcd38f1..ae25c907b7cf 100644 --- a/include/linux/i2c/twl4030.h +++ b/include/linux/i2c/twl4030.h @@ -78,8 +78,8 @@ int twl4030_i2c_read_u8(u8 mod_no, u8 *val, u8 reg); * IMPORTANT: For twl4030_i2c_write(), allocate num_bytes + 1 * for the value, and populate your data starting at offset 1. */ -int twl4030_i2c_write(u8 mod_no, u8 *value, u8 reg, u8 num_bytes); -int twl4030_i2c_read(u8 mod_no, u8 *value, u8 reg, u8 num_bytes); +int twl4030_i2c_write(u8 mod_no, u8 *value, u8 reg, unsigned num_bytes); +int twl4030_i2c_read(u8 mod_no, u8 *value, u8 reg, unsigned num_bytes); /*----------------------------------------------------------------------*/ -- cgit v1.2.2 From 14431aa0c5a443d13d24e6f865a8838f97dab973 Mon Sep 17 00:00:00 2001 From: Mark Brown Date: Sun, 16 Nov 2008 20:16:47 +0100 Subject: power_supply: Add support for WM8350 PMU This patch adds support for the PMU provided by the WM8350 which implements battery, line and USB supplies including a battery charger. The hardware functions largely autonomously, with minimal software control required to initiate fast charging. Support for configuration of the USB supply is not yet implemented. This means that the hardware will remain in the mode configured at startup, by default limiting the current drawn from USB to 100mA. This driver was originally written by Liam Girdwood with subsequent updates for submission by Mark Brown. Signed-off-by: Mark Brown Acked-by: Anton Vorontsov Signed-off-by: Samuel Ortiz --- include/linux/mfd/wm8350/core.h | 26 ++++++++++++++++++++++++++ include/linux/mfd/wm8350/supply.h | 23 ++++++++++++++++++++++- 2 files changed, 48 insertions(+), 1 deletion(-) (limited to 'include/linux') diff --git a/include/linux/mfd/wm8350/core.h b/include/linux/mfd/wm8350/core.h index cc190055b9c4..d2614dfc9397 100644 --- a/include/linux/mfd/wm8350/core.h +++ b/include/linux/mfd/wm8350/core.h @@ -57,6 +57,9 @@ #define WM8350_OVER_CURRENT_INT_STATUS_MASK 0x25 #define WM8350_GPIO_INT_STATUS_MASK 0x26 #define WM8350_COMPARATOR_INT_STATUS_MASK 0x27 +#define WM8350_MISC_OVERRIDES 0xE3 +#define WM8350_COMPARATOR_OVERRIDES 0xE7 +#define WM8350_STATE_MACHINE_STATUS 0xE9 #define WM8350_MAX_REGISTER 0xFF @@ -523,6 +526,29 @@ #define WM8350_DC2_STS 0x0002 #define WM8350_DC1_STS 0x0001 +/* + * R227 (0xE3) - Misc Overrides + */ +#define WM8350_USB_LIMIT_OVRDE 0x0400 + +/* + * R227 (0xE7) - Comparator Overrides + */ +#define WM8350_USB_FB_OVRDE 0x8000 +#define WM8350_WALL_FB_OVRDE 0x4000 +#define WM8350_BATT_FB_OVRDE 0x2000 + + +/* + * R233 (0xE9) - State Machinine Status + */ +#define WM8350_USB_SM_MASK 0x0700 +#define WM8350_USB_SM_SHIFT 8 + +#define WM8350_USB_SM_100_SLV 1 +#define WM8350_USB_SM_500_SLV 5 +#define WM8350_USB_SM_STDBY_SLV 7 + /* WM8350 wake up conditions */ #define WM8350_IRQ_WKUP_OFF_STATE 43 #define WM8350_IRQ_WKUP_HIB_STATE 44 diff --git a/include/linux/mfd/wm8350/supply.h b/include/linux/mfd/wm8350/supply.h index 1c8f3cde79b0..79721513fa9f 100644 --- a/include/linux/mfd/wm8350/supply.h +++ b/include/linux/mfd/wm8350/supply.h @@ -13,7 +13,8 @@ #ifndef __LINUX_MFD_WM8350_SUPPLY_H_ #define __LINUX_MFD_WM8350_SUPPLY_H_ -#include +#include +#include /* * Charger registers @@ -104,8 +105,28 @@ #define WM8350_IRQ_EXT_WALL_FB 37 #define WM8350_IRQ_EXT_BAT_FB 38 +/* + * Policy to control charger state machine. + */ +struct wm8350_charger_policy { + + /* charger state machine policy - set in machine driver */ + int eoc_mA; /* end of charge current (mA) */ + int charge_mV; /* charge voltage */ + int fast_limit_mA; /* fast charge current limit */ + int fast_limit_USB_mA; /* USB fast charge current limit */ + int charge_timeout; /* charge timeout (mins) */ + int trickle_start_mV; /* trickle charge starts at mV */ + int trickle_charge_mA; /* trickle charge current */ + int trickle_charge_USB_mA; /* USB trickle charge current */ +}; + struct wm8350_power { struct platform_device *pdev; + struct power_supply battery; + struct power_supply usb; + struct power_supply ac; + struct wm8350_charger_policy *policy; }; #endif -- cgit v1.2.2 From d756f4a4446227ca9626087939a6769ca55ab036 Mon Sep 17 00:00:00 2001 From: Mark Brown Date: Mon, 24 Nov 2008 20:20:30 +0100 Subject: mfd: Switch WM8350 revision detection to a feature based model Rather than check for chip revisions in the WM8350 drivers have the core code set flags for relevant differences. Signed-off-by: Mark Brown Signed-off-by: Samuel Ortiz --- include/linux/mfd/wm8350/core.h | 2 -- include/linux/mfd/wm8350/supply.h | 2 ++ 2 files changed, 2 insertions(+), 2 deletions(-) (limited to 'include/linux') diff --git a/include/linux/mfd/wm8350/core.h b/include/linux/mfd/wm8350/core.h index d2614dfc9397..3c9735663f36 100644 --- a/include/linux/mfd/wm8350/core.h +++ b/include/linux/mfd/wm8350/core.h @@ -585,8 +585,6 @@ struct wm8350_irq { }; struct wm8350 { - int rev; /* chip revision */ - struct device *dev; /* device IO */ diff --git a/include/linux/mfd/wm8350/supply.h b/include/linux/mfd/wm8350/supply.h index 79721513fa9f..2b9479310bbd 100644 --- a/include/linux/mfd/wm8350/supply.h +++ b/include/linux/mfd/wm8350/supply.h @@ -127,6 +127,8 @@ struct wm8350_power { struct power_supply usb; struct power_supply ac; struct wm8350_charger_policy *policy; + + int rev_g_coeff; }; #endif -- cgit v1.2.2 From b797a5551979da22b0a35632198ffc8a330d9537 Mon Sep 17 00:00:00 2001 From: Mark Brown Date: Mon, 24 Nov 2008 20:22:58 +0100 Subject: mfd: Refactor WM8350 chip identification Since the WM8350 driver was originally written the semantics for the identification registers of the chip have been clarified, allowing us to do an exact match on all the fields. This avoids mistakenly running on unsupported hardware. Also change to using the datasheet names more consistently for legibility and fix a printk() that should be dev_err(). Signed-off-by: Mark Brown Signed-off-by: Samuel Ortiz --- include/linux/mfd/wm8350/core.h | 6 ++++++ 1 file changed, 6 insertions(+) (limited to 'include/linux') diff --git a/include/linux/mfd/wm8350/core.h b/include/linux/mfd/wm8350/core.h index 3c9735663f36..2a7abeebe777 100644 --- a/include/linux/mfd/wm8350/core.h +++ b/include/linux/mfd/wm8350/core.h @@ -29,6 +29,7 @@ */ #define WM8350_RESET_ID 0x00 #define WM8350_ID 0x01 +#define WM8350_REVISION 0x02 #define WM8350_SYSTEM_CONTROL_1 0x03 #define WM8350_SYSTEM_CONTROL_2 0x04 #define WM8350_SYSTEM_HIBERNATE 0x05 @@ -79,6 +80,11 @@ #define WM8350_CONF_STS_MASK 0x0C00 #define WM8350_CUST_ID_MASK 0x00FF +/* + * R2 (0x02) - Revision + */ +#define WM8350_MASK_REV_MASK 0x00FF + /* * R3 (0x03) - System Control 1 */ -- cgit v1.2.2 From 7e386e6e0e4f34f0545e8923e22fe4dd61ef9d48 Mon Sep 17 00:00:00 2001 From: Mark Brown Date: Sun, 30 Nov 2008 22:43:21 +0100 Subject: power_supply: Add cold to the POWER_SUPPLY_HEALTH report values Some systems are able to report problems with batteries being under temperature. Signed-off-by: Mark Brown Acked-by: Anton Vorontsov Signed-off-by: Samuel Ortiz --- include/linux/power_supply.h | 1 + 1 file changed, 1 insertion(+) (limited to 'include/linux') diff --git a/include/linux/power_supply.h b/include/linux/power_supply.h index f9348cba6dc1..8ff25e0e7f7a 100644 --- a/include/linux/power_supply.h +++ b/include/linux/power_supply.h @@ -45,6 +45,7 @@ enum { POWER_SUPPLY_HEALTH_DEAD, POWER_SUPPLY_HEALTH_OVERVOLTAGE, POWER_SUPPLY_HEALTH_UNSPEC_FAILURE, + POWER_SUPPLY_HEALTH_COLD, }; enum { -- cgit v1.2.2 From 4008e879e1325c29362aa2c3fa4b527273ae15a8 Mon Sep 17 00:00:00 2001 From: Mark Brown Date: Sun, 30 Nov 2008 22:45:14 +0100 Subject: power_supply: Add battery health reporting for WM8350 Implement support for reporting battery health in the WM8350 battery interface. Since we are now able to report this via the classs remove the diagnostics from the interrupt handler. Signed-off-by: Mark Brown Acked-by: Anton Vorontsov Signed-off-by: Samuel Ortiz --- include/linux/mfd/wm8350/core.h | 7 +++++++ 1 file changed, 7 insertions(+) (limited to 'include/linux') diff --git a/include/linux/mfd/wm8350/core.h b/include/linux/mfd/wm8350/core.h index 2a7abeebe777..afeff6f1316c 100644 --- a/include/linux/mfd/wm8350/core.h +++ b/include/linux/mfd/wm8350/core.h @@ -58,6 +58,7 @@ #define WM8350_OVER_CURRENT_INT_STATUS_MASK 0x25 #define WM8350_GPIO_INT_STATUS_MASK 0x26 #define WM8350_COMPARATOR_INT_STATUS_MASK 0x27 +#define WM8350_CHARGER_OVERRIDES 0xE2 #define WM8350_MISC_OVERRIDES 0xE3 #define WM8350_COMPARATOR_OVERRIDES 0xE7 #define WM8350_STATE_MACHINE_STATUS 0xE9 @@ -532,6 +533,12 @@ #define WM8350_DC2_STS 0x0002 #define WM8350_DC1_STS 0x0001 +/* + * R226 (0xE2) - Charger status + */ +#define WM8350_CHG_BATT_HOT_OVRDE 0x8000 +#define WM8350_CHG_BATT_COLD_OVRDE 0x4000 + /* * R227 (0xE3) - Misc Overrides */ -- cgit v1.2.2 From 67460a7c26271fd7a32e5d51b2c806a84ce78a62 Mon Sep 17 00:00:00 2001 From: David Brownell Date: Mon, 1 Dec 2008 00:35:33 +0100 Subject: mfd: twl4030: cleanup symbols and OMAP dependency Finish removing dependency of TWL driver stack on platform-specific IRQ definitions ... and remove the build dependency on OMAP. This lets the TWL4030 code be included in test builds for most platforms, and will make it easier for non-OMAP folk to update most of this code for new APIs etc. Signed-off-by: David Brownell Signed-off-by: Tony Lindgren Signed-off-by: Samuel Ortiz --- include/linux/i2c/twl4030.h | 31 ------------------------------- 1 file changed, 31 deletions(-) (limited to 'include/linux') diff --git a/include/linux/i2c/twl4030.h b/include/linux/i2c/twl4030.h index ae25c907b7cf..d4846695bcd0 100644 --- a/include/linux/i2c/twl4030.h +++ b/include/linux/i2c/twl4030.h @@ -285,33 +285,6 @@ struct twl4030_platform_data { int twl4030_sih_setup(int module); -/* - * FIXME completely stop using TWL4030_IRQ_BASE ... instead, pass the - * IRQ data to subsidiary devices using platform device resources. - */ - -/* IRQ information-need base */ -#include -/* TWL4030 interrupts */ - -/* #define TWL4030_MODIRQ_GPIO (TWL4030_IRQ_BASE + 0) */ -#define TWL4030_MODIRQ_KEYPAD (TWL4030_IRQ_BASE + 1) -#define TWL4030_MODIRQ_BCI (TWL4030_IRQ_BASE + 2) -#define TWL4030_MODIRQ_MADC (TWL4030_IRQ_BASE + 3) -/* #define TWL4030_MODIRQ_USB (TWL4030_IRQ_BASE + 4) */ -/* #define TWL4030_MODIRQ_PWR (TWL4030_IRQ_BASE + 5) */ - -#define TWL4030_PWRIRQ_PWRBTN (TWL4030_PWR_IRQ_BASE + 0) -/* #define TWL4030_PWRIRQ_CHG_PRES (TWL4030_PWR_IRQ_BASE + 1) */ -/* #define TWL4030_PWRIRQ_USB_PRES (TWL4030_PWR_IRQ_BASE + 2) */ -/* #define TWL4030_PWRIRQ_RTC (TWL4030_PWR_IRQ_BASE + 3) */ -/* #define TWL4030_PWRIRQ_HOT_DIE (TWL4030_PWR_IRQ_BASE + 4) */ -/* #define TWL4030_PWRIRQ_PWROK_TIMEOUT (TWL4030_PWR_IRQ_BASE + 5) */ -/* #define TWL4030_PWRIRQ_MBCHG (TWL4030_PWR_IRQ_BASE + 6) */ -/* #define TWL4030_PWRIRQ_SC_DETECT (TWL4030_PWR_IRQ_BASE + 7) */ - -/* Rest are unsued currently*/ - /* Offsets to Power Registers */ #define TWL4030_VDAC_DEV_GRP 0x3B #define TWL4030_VDAC_DEDICATED 0x3E @@ -322,10 +295,6 @@ int twl4030_sih_setup(int module); #define TWL4030_VAUX3_DEV_GRP 0x1F #define TWL4030_VAUX3_DEDICATED 0x22 -/* TWL4030 GPIO interrupt definitions */ - -#define TWL4030_GPIO_IRQ_NO(n) (TWL4030_GPIO_IRQ_BASE + (n)) - /* * Exported TWL4030 GPIO APIs * -- cgit v1.2.2 From dad759ff8ba79927766e3f0159bfc5fb6de0f982 Mon Sep 17 00:00:00 2001 From: David Brownell Date: Mon, 1 Dec 2008 00:43:58 +0100 Subject: mfd: twl4030: create some regulator devices Initial code to create twl4030 voltage regulator devices, using the new regulator framework. Note that this now starts to care what name is used to declare the TWL chip: - TWL4030 is the "old" chip; newer ones have a bigger variety of VAUX2 voltages. - TWL5030 is the core "new" chip; TPS65950 is its catalog version. - The TPS65930 and TPS65920 are cost-reduced catalog versions of TWL5030 parts ... fewer regulators, no battery charger, etc. Board-specific regulator configuration should be provided, listing which regulators are used and their constraints (e.g. 1.8V only). Code that could ("should"?) leverage the regulator stuff includes TWL4030 USB transceiver support and MMC glue, LCD support for the 3430SDP and Labrador boards, and S-Video output. Signed-off-by: David Brownell Signed-off-by: Tony Lindgren Signed-off-by: Samuel Ortiz --- include/linux/i2c/twl4030.h | 47 +++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 47 insertions(+) (limited to 'include/linux') diff --git a/include/linux/i2c/twl4030.h b/include/linux/i2c/twl4030.h index d4846695bcd0..e06555d40d35 100644 --- a/include/linux/i2c/twl4030.h +++ b/include/linux/i2c/twl4030.h @@ -278,6 +278,18 @@ struct twl4030_platform_data { struct twl4030_keypad_data *keypad; struct twl4030_usb_data *usb; + /* LDO regulators */ + struct regulator_init_data *vdac; + struct regulator_init_data *vpll1; + struct regulator_init_data *vpll2; + struct regulator_init_data *vmmc1; + struct regulator_init_data *vmmc2; + struct regulator_init_data *vsim; + struct regulator_init_data *vaux1; + struct regulator_init_data *vaux2; + struct regulator_init_data *vaux3; + struct regulator_init_data *vaux4; + /* REVISIT more to come ... _nothing_ should be hard-wired */ }; @@ -309,4 +321,39 @@ int twl4030_set_gpio_debounce(int gpio, int enable); static inline int twl4030charger_usb_en(int enable) { return 0; } #endif +/*----------------------------------------------------------------------*/ + +/* Linux-specific regulator identifiers ... for now, we only support + * the LDOs, and leave the three buck converters alone. VDD1 and VDD2 + * need to tie into hardware based voltage scaling (cpufreq etc), while + * VIO is generally fixed. + */ + +/* EXTERNAL dc-to-dc buck converters */ +#define TWL4030_REG_VDD1 0 +#define TWL4030_REG_VDD2 1 +#define TWL4030_REG_VIO 2 + +/* EXTERNAL LDOs */ +#define TWL4030_REG_VDAC 3 +#define TWL4030_REG_VPLL1 4 +#define TWL4030_REG_VPLL2 5 /* not on all chips */ +#define TWL4030_REG_VMMC1 6 +#define TWL4030_REG_VMMC2 7 /* not on all chips */ +#define TWL4030_REG_VSIM 8 /* not on all chips */ +#define TWL4030_REG_VAUX1 9 /* not on all chips */ +#define TWL4030_REG_VAUX2_4030 10 /* (twl4030-specific) */ +#define TWL4030_REG_VAUX2 11 /* (twl5030 and newer) */ +#define TWL4030_REG_VAUX3 12 /* not on all chips */ +#define TWL4030_REG_VAUX4 13 /* not on all chips */ + +/* INTERNAL LDOs */ +#define TWL4030_REG_VINTANA1 14 +#define TWL4030_REG_VINTANA2 15 +#define TWL4030_REG_VINTDIG 16 +#define TWL4030_REG_VUSB1V5 17 +#define TWL4030_REG_VUSB1V8 18 +#define TWL4030_REG_VUSB3V1 19 +#define TWL4030_REG_VUSBCP 20 + #endif /* End of __TWL4030_H */ -- cgit v1.2.2 From b73eac7871d002835be17d4602cced2c15c0db4b Mon Sep 17 00:00:00 2001 From: David Brownell Date: Sun, 7 Dec 2008 19:10:58 +0100 Subject: mfd: twl4030 regulator bug fixes This contains two bugfixes to the initial twl4030 regulator support patch related to USB: (a) always overwrite the old list of consumers ... else the regulator handles all use the same "usb1v5" name; (b) don't set up the "usbcp" regulator, which turns out to be managed through separate controls, usually ULPI directly from the OTG controller. Signed-off-by: David Brownell Signed-off-by: Samuel Ortiz --- include/linux/i2c/twl4030.h | 1 - 1 file changed, 1 deletion(-) (limited to 'include/linux') diff --git a/include/linux/i2c/twl4030.h b/include/linux/i2c/twl4030.h index e06555d40d35..a8f84c01f82e 100644 --- a/include/linux/i2c/twl4030.h +++ b/include/linux/i2c/twl4030.h @@ -354,6 +354,5 @@ int twl4030_set_gpio_debounce(int gpio, int enable); #define TWL4030_REG_VUSB1V5 17 #define TWL4030_REG_VUSB1V8 18 #define TWL4030_REG_VUSB3V1 19 -#define TWL4030_REG_VUSBCP 20 #endif /* End of __TWL4030_H */ -- cgit v1.2.2 From 856f6fd119411d5701d5db96e1aae1dd69923887 Mon Sep 17 00:00:00 2001 From: Mike Rapoport Date: Thu, 18 Dec 2008 10:54:27 +0100 Subject: mfd: Dialog DA9030 battery charger MFD driver This patch amends DA903x MFD driver with definitions and methods needed for battery charger driver. Signed-off-by: Mike Rapoport Signed-off-by: Samuel Ortiz --- include/linux/mfd/da903x.h | 44 ++++++++++++++++++++++++++++++++++++++++++-- 1 file changed, 42 insertions(+), 2 deletions(-) (limited to 'include/linux') diff --git a/include/linux/mfd/da903x.h b/include/linux/mfd/da903x.h index cad314c12439..115dbe965082 100644 --- a/include/linux/mfd/da903x.h +++ b/include/linux/mfd/da903x.h @@ -32,6 +32,7 @@ enum { DA9030_ID_LDO18, DA9030_ID_LDO19, DA9030_ID_LDO_INT, /* LDO Internal */ + DA9030_ID_BAT, /* battery charger */ DA9034_ID_LED_1, DA9034_ID_LED_2, @@ -93,6 +94,43 @@ struct da9034_touch_pdata { int y_inverted; }; +/* DA9030 battery charger data */ +struct power_supply_info; + +struct da9030_battery_info { + /* battery parameters */ + struct power_supply_info *battery_info; + + /* current and voltage to use for battery charging */ + unsigned int charge_milliamp; + unsigned int charge_millivolt; + + /* voltage thresholds (in millivolts) */ + int vbat_low; + int vbat_crit; + int vbat_charge_start; + int vbat_charge_stop; + int vbat_charge_restart; + + /* battery nominal minimal and maximal voltages in millivolts */ + int vcharge_min; + int vcharge_max; + + /* Temperature thresholds. These are DA9030 register values + "as is" and should be measured for each battery type */ + int tbat_low; + int tbat_high; + int tbat_restart; + + + /* battery monitor interval (seconds) */ + unsigned int batmon_interval; + + /* platform callbacks for battery low and critical events */ + void (*battery_low)(void); + void (*battery_critical)(void); +}; + struct da903x_subdev_info { int id; const char *name; @@ -190,11 +228,13 @@ extern int da903x_unregister_notifier(struct device *dev, extern int da903x_query_status(struct device *dev, unsigned int status); -/* NOTE: the two functions below are not intended for use outside - * of the DA9034 sub-device drivers +/* NOTE: the functions below are not intended for use outside + * of the DA903x sub-device drivers */ extern int da903x_write(struct device *dev, int reg, uint8_t val); +extern int da903x_writes(struct device *dev, int reg, int len, uint8_t *val); extern int da903x_read(struct device *dev, int reg, uint8_t *val); +extern int da903x_reads(struct device *dev, int reg, int len, uint8_t *val); extern int da903x_update(struct device *dev, int reg, uint8_t val, uint8_t mask); extern int da903x_set_bits(struct device *dev, int reg, uint8_t bit_mask); extern int da903x_clr_bits(struct device *dev, int reg, uint8_t bit_mask); -- cgit v1.2.2 From 96920630624868add3f63f596523e70dbb64549a Mon Sep 17 00:00:00 2001 From: Mark Brown Date: Thu, 18 Dec 2008 23:09:50 +0100 Subject: mfd: Add WM8352 support The WM8352 is a variant of the WM8350. Aside from the register defaults there are no software visible differences to the WM8350. Signed-off-by: Mark Brown Signed-off-by: Samuel Ortiz --- include/linux/mfd/wm8350/core.h | 4 ++++ 1 file changed, 4 insertions(+) (limited to 'include/linux') diff --git a/include/linux/mfd/wm8350/core.h b/include/linux/mfd/wm8350/core.h index afeff6f1316c..737579086d01 100644 --- a/include/linux/mfd/wm8350/core.h +++ b/include/linux/mfd/wm8350/core.h @@ -589,6 +589,10 @@ extern const u16 wm8350_mode0_defaults[]; extern const u16 wm8350_mode1_defaults[]; extern const u16 wm8350_mode2_defaults[]; extern const u16 wm8350_mode3_defaults[]; +extern const u16 wm8352_mode0_defaults[]; +extern const u16 wm8352_mode1_defaults[]; +extern const u16 wm8352_mode2_defaults[]; +extern const u16 wm8352_mode3_defaults[]; struct wm8350; -- cgit v1.2.2 From 645524a9c6e1e42dc4fe03217befb20e2fc4d43e Mon Sep 17 00:00:00 2001 From: Mark Brown Date: Thu, 18 Dec 2008 23:12:16 +0100 Subject: mfd: Support configurable numbers of DCDCs and ISINKs on WM8350 Some WM8350 variants have fewer DCDCs and ISINKs. Identify these at probe and refuse to use the absent DCDCs when running on these chips. Signed-off-by: Mark Brown Signed-off-by: Samuel Ortiz --- include/linux/mfd/wm8350/pmic.h | 4 ++++ 1 file changed, 4 insertions(+) (limited to 'include/linux') diff --git a/include/linux/mfd/wm8350/pmic.h b/include/linux/mfd/wm8350/pmic.h index 69b69e07f62f..96acbfc8aa12 100644 --- a/include/linux/mfd/wm8350/pmic.h +++ b/include/linux/mfd/wm8350/pmic.h @@ -701,6 +701,10 @@ struct platform_device; struct regulator_init_data; struct wm8350_pmic { + /* Number of regulators of each type on this device */ + int max_dcdc; + int max_isink; + /* ISINK to DCDC mapping */ int isink_A_dcdc; int isink_B_dcdc; -- cgit v1.2.2 From ca23f8c1b0aa15dc69565244fc5dffa67a72dd02 Mon Sep 17 00:00:00 2001 From: Mark Brown Date: Thu, 18 Dec 2008 23:12:28 +0100 Subject: mfd: Add WM8351 support The WM8351 is a WM8350 variant. As well as register default changes the WM8351 has fewer voltage and current regulators than the WM8350. Signed-off-by: Mark Brown Signed-off-by: Samuel Ortiz --- include/linux/mfd/wm8350/core.h | 4 ++++ 1 file changed, 4 insertions(+) (limited to 'include/linux') diff --git a/include/linux/mfd/wm8350/core.h b/include/linux/mfd/wm8350/core.h index 737579086d01..980669d50dca 100644 --- a/include/linux/mfd/wm8350/core.h +++ b/include/linux/mfd/wm8350/core.h @@ -589,6 +589,10 @@ extern const u16 wm8350_mode0_defaults[]; extern const u16 wm8350_mode1_defaults[]; extern const u16 wm8350_mode2_defaults[]; extern const u16 wm8350_mode3_defaults[]; +extern const u16 wm8351_mode0_defaults[]; +extern const u16 wm8351_mode1_defaults[]; +extern const u16 wm8351_mode2_defaults[]; +extern const u16 wm8351_mode3_defaults[]; extern const u16 wm8352_mode0_defaults[]; extern const u16 wm8352_mode1_defaults[]; extern const u16 wm8352_mode2_defaults[]; -- cgit v1.2.2 From 0931a4c6dbfab03f2bfd22a9170130f7b155d53a Mon Sep 17 00:00:00 2001 From: David Brownell Date: Mon, 22 Dec 2008 12:05:27 +0100 Subject: mfd: dm355evm msp430 driver Basic MFD framework for the MSP430 microcontroller firmware used on the dm355evm board: - Provides an interface for other drivers: register read/write utilities, and register declarations. - Directly exports: * Many signals through the GPIO framework + LEDs + SW6 through gpio sysfs + NTSC/nPAL jumper through gpio sysfs + ... more could be added later, e.g. MMC signals * Child devices: + LEDs, via leds-gpio child (and default triggers) + RTC, via rtc-dm355evm child device + Buttons and IR control, via dm355evm_keys - Supports power-off system call. Use the reset button to power the board back up; the power supply LED will be on, but the MSP430 waits to re-activate the regulators. - On probe() this: * Announces firmware revision * Turns off the banked LEDs * Exports the resources noted above * Hooks the power-off support * Muxes tvp5146 -or- imager for video input Unless the new tvp514x driver (tracked for mainline) is configured, this assumes that some custom imager driver handles video-in. This completely ignores the registers reporting the output voltages on the various power supplies. Someone could add a hwmon interface if that seems useful. Signed-off-by: David Brownell Signed-off-by: Samuel Ortiz --- include/linux/i2c/dm355evm_msp.h | 79 ++++++++++++++++++++++++++++++++++++++++ 1 file changed, 79 insertions(+) create mode 100644 include/linux/i2c/dm355evm_msp.h (limited to 'include/linux') diff --git a/include/linux/i2c/dm355evm_msp.h b/include/linux/i2c/dm355evm_msp.h new file mode 100644 index 000000000000..372470350fab --- /dev/null +++ b/include/linux/i2c/dm355evm_msp.h @@ -0,0 +1,79 @@ +/* + * dm355evm_msp.h - support MSP430 microcontroller on DM355EVM board + */ +#ifndef __LINUX_I2C_DM355EVM_MSP +#define __LINUX_I2C_DM355EVM_MSP + +/* + * Written against Spectrum's writeup for the A4 firmware revision, + * and tweaked to match source and rev D2 schematics by removing CPLD + * and NOR flash hooks (which were last appropriate in rev B boards). + * + * Note that the firmware supports a flavor of write posting ... to be + * sure a write completes, issue another read or write. + */ + +/* utilities to access "registers" emulated by msp430 firmware */ +extern int dm355evm_msp_write(u8 value, u8 reg); +extern int dm355evm_msp_read(u8 reg); + + +/* command/control registers */ +#define DM355EVM_MSP_COMMAND 0x00 +# define MSP_COMMAND_NULL 0 +# define MSP_COMMAND_RESET_COLD 1 +# define MSP_COMMAND_RESET_WARM 2 +# define MSP_COMMAND_RESET_WARM_I 3 +# define MSP_COMMAND_POWEROFF 4 +# define MSP_COMMAND_IR_REINIT 5 +#define DM355EVM_MSP_STATUS 0x01 +# define MSP_STATUS_BAD_OFFSET BIT(0) +# define MSP_STATUS_BAD_COMMAND BIT(1) +# define MSP_STATUS_POWER_ERROR BIT(2) +# define MSP_STATUS_RXBUF_OVERRUN BIT(3) +#define DM355EVM_MSP_RESET 0x02 /* 0 bits == in reset */ +# define MSP_RESET_DC5 BIT(0) +# define MSP_RESET_TVP5154 BIT(2) +# define MSP_RESET_IMAGER BIT(3) +# define MSP_RESET_ETHERNET BIT(4) +# define MSP_RESET_SYS BIT(5) +# define MSP_RESET_AIC33 BIT(7) + +/* GPIO registers ... bit patterns mostly match the source MSP ports */ +#define DM355EVM_MSP_LED 0x03 /* active low (MSP P4) */ +#define DM355EVM_MSP_SWITCH1 0x04 /* (MSP P5, masked) */ +# define MSP_SWITCH1_SW6_1 BIT(0) +# define MSP_SWITCH1_SW6_2 BIT(1) +# define MSP_SWITCH1_SW6_3 BIT(2) +# define MSP_SWITCH1_SW6_4 BIT(3) +# define MSP_SWITCH1_J1 BIT(4) /* NTSC/PAL */ +# define MSP_SWITCH1_MSP_INT BIT(5) /* active low */ +#define DM355EVM_MSP_SWITCH2 0x05 /* (MSP P6, masked) */ +# define MSP_SWITCH2_SW10 BIT(3) +# define MSP_SWITCH2_SW11 BIT(4) +# define MSP_SWITCH2_SW12 BIT(5) +# define MSP_SWITCH2_SW13 BIT(6) +# define MSP_SWITCH2_SW14 BIT(7) +#define DM355EVM_MSP_SDMMC 0x06 /* (MSP P2, masked) */ +# define MSP_SDMMC_0_WP BIT(1) +# define MSP_SDMMC_0_CD BIT(2) /* active low */ +# define MSP_SDMMC_1_WP BIT(3) +# define MSP_SDMMC_1_CD BIT(4) /* active low */ +#define DM355EVM_MSP_FIRMREV 0x07 /* not a GPIO (out of order) */ +#define DM355EVM_MSP_VIDEO_IN 0x08 /* (MSP P3, masked) */ +# define MSP_VIDEO_IMAGER BIT(7) /* low == tvp5146 */ + +/* power supply registers are currently omitted */ + +/* RTC registers */ +#define DM355EVM_MSP_RTC_0 0x12 /* LSB */ +#define DM355EVM_MSP_RTC_1 0x13 +#define DM355EVM_MSP_RTC_2 0x14 +#define DM355EVM_MSP_RTC_3 0x15 /* MSB */ + +/* input event queue registers; code == ((HIGH << 8) | LOW) */ +#define DM355EVM_MSP_INPUT_COUNT 0x16 /* decrement by reading LOW */ +#define DM355EVM_MSP_INPUT_HIGH 0x17 +#define DM355EVM_MSP_INPUT_LOW 0x18 + +#endif /* __LINUX_I2C_DM355EVM_MSP */ -- cgit v1.2.2 From 088af9a6e05d51e7c3dc85d45d8b7a52c3ee08d7 Mon Sep 17 00:00:00 2001 From: Helge Deller Date: Wed, 31 Dec 2008 12:31:18 +0100 Subject: module: fix module loading failure of large kernel modules for parisc When creating the final layout of a kernel module in memory, allow the module loader to reserve some additional memory in front of a given section. This is currently only needed for the parisc port which needs to put the stub entries there to fulfill the 17/22bit PCREL relocations with large kernel modules like xfs. Signed-off-by: Helge Deller Signed-off-by: Rusty Russell (renamed fn) --- include/linux/moduleloader.h | 3 +++ 1 file changed, 3 insertions(+) (limited to 'include/linux') diff --git a/include/linux/moduleloader.h b/include/linux/moduleloader.h index eb1033957486..c1f40c2f7ffb 100644 --- a/include/linux/moduleloader.h +++ b/include/linux/moduleloader.h @@ -13,6 +13,9 @@ int module_frob_arch_sections(Elf_Ehdr *hdr, char *secstrings, struct module *mod); +/* Additional bytes needed by arch in front of individual sections */ +unsigned int arch_mod_section_prepend(struct module *mod, unsigned int section); + /* Allocator used for allocating struct module, core sections and init sections. Returns NULL on failure. */ void *module_alloc(unsigned long size); -- cgit v1.2.2 From 9ea09af3bd3090e8349ca2899ca2011bd94cda85 Mon Sep 17 00:00:00 2001 From: Heiko Carstens Date: Mon, 22 Dec 2008 12:36:30 +0100 Subject: stop_machine: introduce stop_machine_create/destroy. Introduce stop_machine_create/destroy. With this interface subsystems that need a non-failing stop_machine environment can create the stop_machine machine threads before actually calling stop_machine. When the threads aren't needed anymore they can be killed with stop_machine_destroy again. When stop_machine gets called and the threads aren't present they will be created and destroyed automatically. This restores the old behaviour of stop_machine. This patch also converts cpu hotplug to the new interface since it is special: cpu_down calls __stop_machine instead of stop_machine. However the kstop threads will only be created when stop_machine gets called. Changing the code so that the threads would be created automatically on __stop_machine is currently not possible: when __stop_machine gets called we hold cpu_add_remove_lock, which is the same lock that create_rt_workqueue would take. So the workqueue needs to be created before the cpu hotplug code locks cpu_add_remove_lock. Signed-off-by: Heiko Carstens Signed-off-by: Rusty Russell --- include/linux/stop_machine.h | 22 ++++++++++++++++++++++ 1 file changed, 22 insertions(+) (limited to 'include/linux') diff --git a/include/linux/stop_machine.h b/include/linux/stop_machine.h index 74d59a641362..baba3a23a814 100644 --- a/include/linux/stop_machine.h +++ b/include/linux/stop_machine.h @@ -35,6 +35,24 @@ int stop_machine(int (*fn)(void *), void *data, const struct cpumask *cpus); * won't come or go while it's being called. Used by hotplug cpu. */ int __stop_machine(int (*fn)(void *), void *data, const struct cpumask *cpus); + +/** + * stop_machine_create: create all stop_machine threads + * + * Description: This causes all stop_machine threads to be created before + * stop_machine actually gets called. This can be used by subsystems that + * need a non failing stop_machine infrastructure. + */ +int stop_machine_create(void); + +/** + * stop_machine_destroy: destroy all stop_machine threads + * + * Description: This causes all stop_machine threads which were created with + * stop_machine_create to be destroyed again. + */ +void stop_machine_destroy(void); + #else static inline int stop_machine(int (*fn)(void *), void *data, @@ -46,5 +64,9 @@ static inline int stop_machine(int (*fn)(void *), void *data, local_irq_enable(); return ret; } + +static inline int stop_machine_create(void) { return 0; } +static inline void stop_machine_destroy(void) { } + #endif /* CONFIG_SMP */ #endif /* _LINUX_STOP_MACHINE */ -- cgit v1.2.2 From 5d38a079ce3971f932bbdc0dc5b887806fabd5dc Mon Sep 17 00:00:00 2001 From: Herbert Xu Date: Sun, 4 Jan 2009 16:13:40 -0800 Subject: gro: Add page frag support This patch allows GRO to merge page frags (skb_shinfo(skb)->frags) in one skb, rather than using the less efficient frag_list. It also adds a new interface, napi_gro_frags to allow drivers to inject page frags directly into the stack without allocating an skb. This is intended to be the GRO equivalent for LRO's lro_receive_frags interface. The existing GSO interface can already handle page frags with or without an appended frag_list so nothing needs to be changed there. The merging itself is rather simple. We store any new frag entries after the last existing entry, without checking whether the first new entry can be merged with the last existing entry. Making this check would actually be easy but since no existing driver can produce contiguous frags anyway it would just be mental masturbation. If the total number of entries would exceed the capacity of a single skb, we simply resort to using frag_list as we do now. Signed-off-by: Herbert Xu Signed-off-by: David S. Miller --- include/linux/netdevice.h | 16 +++++++++++++++- 1 file changed, 15 insertions(+), 1 deletion(-) (limited to 'include/linux') diff --git a/include/linux/netdevice.h b/include/linux/netdevice.h index 41e1224651cf..c28bbba3c23d 100644 --- a/include/linux/netdevice.h +++ b/include/linux/netdevice.h @@ -313,10 +313,11 @@ struct napi_struct { #ifdef CONFIG_NETPOLL spinlock_t poll_lock; int poll_owner; - struct net_device *dev; #endif + struct net_device *dev; struct list_head dev_list; struct sk_buff *gro_list; + struct sk_buff *skb; }; enum @@ -990,6 +991,9 @@ struct napi_gro_cb { /* Number of segments aggregated. */ int count; + + /* Free the skb? */ + int free; }; #define NAPI_GRO_CB(skb) ((struct napi_gro_cb *)(skb)->cb) @@ -1011,6 +1015,14 @@ struct packet_type { struct list_head list; }; +struct napi_gro_fraginfo { + skb_frag_t frags[MAX_SKB_FRAGS]; + unsigned int nr_frags; + unsigned int ip_summed; + unsigned int len; + __wsum csum; +}; + #include #include @@ -1363,6 +1375,8 @@ extern int netif_receive_skb(struct sk_buff *skb); extern void napi_gro_flush(struct napi_struct *napi); extern int napi_gro_receive(struct napi_struct *napi, struct sk_buff *skb); +extern int napi_gro_frags(struct napi_struct *napi, + struct napi_gro_fraginfo *info); extern void netif_nit_deliver(struct sk_buff *skb); extern int dev_valid_name(const char *name); extern int dev_ioctl(struct net *net, unsigned int cmd, void __user *); -- cgit v1.2.2 From e9079cce201784632aed4b1a3121ee38c1ced0b6 Mon Sep 17 00:00:00 2001 From: Steven Whitehouse Date: Tue, 14 Oct 2008 14:43:29 +0100 Subject: GFS2: Support for FIEMAP ioctl This patch implements the FIEMAP ioctl for GFS2. We can use the generic code (aside from a lock order issue, solved as per Ted Tso's suggestion) for which I've introduced a new variant of the generic function. We also have one exception to deal with, namely stuffed files, so we do that "by hand", setting all the required flags. This has been tested with a modified (I could only find an old version) of Eric's test program, and appears to work correctly. This patch does not currently support FIEMAP of xattrs, but the plan is to add that feature at some future point. Signed-off-by: Steven Whitehouse Cc: Theodore Tso Cc: Eric Sandeen --- include/linux/fs.h | 3 +++ 1 file changed, 3 insertions(+) (limited to 'include/linux') diff --git a/include/linux/fs.h b/include/linux/fs.h index f2a3010140e3..e34bc6925fdf 100644 --- a/include/linux/fs.h +++ b/include/linux/fs.h @@ -2059,6 +2059,9 @@ extern int vfs_fstat(unsigned int, struct kstat *); extern int do_vfs_ioctl(struct file *filp, unsigned int fd, unsigned int cmd, unsigned long arg); +extern int __generic_block_fiemap(struct inode *inode, + struct fiemap_extent_info *fieinfo, u64 start, + u64 len, get_block_t *get_block); extern int generic_block_fiemap(struct inode *inode, struct fiemap_extent_info *fieinfo, u64 start, u64 len, get_block_t *get_block); -- cgit v1.2.2 From 74f783af95c982aef6d3a1415275650dcf511666 Mon Sep 17 00:00:00 2001 From: Jan Kara Date: Tue, 19 Aug 2008 14:51:22 +0200 Subject: quota: Add callbacks for allocating and destroying dquot structures Some filesystems would like to keep private information together with each dquot. Add callbacks alloc_dquot and destroy_dquot allowing filesystem to allocate larger dquots from their private slab in a similar fashion we currently allocate inodes. Signed-off-by: Jan Kara Signed-off-by: Mark Fasheh --- include/linux/quota.h | 2 ++ 1 file changed, 2 insertions(+) (limited to 'include/linux') diff --git a/include/linux/quota.h b/include/linux/quota.h index 40401b554484..3ce708c2cb3c 100644 --- a/include/linux/quota.h +++ b/include/linux/quota.h @@ -292,6 +292,8 @@ struct dquot_operations { int (*free_inode) (const struct inode *, unsigned long); int (*transfer) (struct inode *, struct iattr *); int (*write_dquot) (struct dquot *); /* Ordinary dquot write */ + struct dquot *(*alloc_dquot)(struct super_block *, int); /* Allocate memory for new dquot */ + void (*destroy_dquot)(struct dquot *); /* Free memory for dquot */ int (*acquire_dquot) (struct dquot *); /* Quota is going to be created on disk */ int (*release_dquot) (struct dquot *); /* Quota is going to be deleted from disk */ int (*mark_dirty) (struct dquot *); /* Dquot is marked dirty */ -- cgit v1.2.2 From 12095460f7f315f8ef67a55b2194195d325d48d7 Mon Sep 17 00:00:00 2001 From: Jan Kara Date: Wed, 20 Aug 2008 14:45:12 +0200 Subject: quota: Increase size of variables for limits and inode usage So far quota was fine with quota block limits and inode limits/numbers in a 32-bit type. Now with rapid increase in storage sizes there are coming requests to be able to handle quota limits above 4TB / more that 2^32 inodes. So bump up sizes of types in mem_dqblk structure to 64-bits to be able to handle this. Also update inode allocation / checking functions to use qsize_t and make global structure keep quota limits in bytes so that things are consistent. Signed-off-by: Jan Kara Signed-off-by: Mark Fasheh --- include/linux/quota.h | 28 ++++++++++++---------------- include/linux/quotaops.h | 4 ++-- 2 files changed, 14 insertions(+), 18 deletions(-) (limited to 'include/linux') diff --git a/include/linux/quota.h b/include/linux/quota.h index 3ce708c2cb3c..9ea468363f9f 100644 --- a/include/linux/quota.h +++ b/include/linux/quota.h @@ -39,15 +39,6 @@ #define __DQUOT_VERSION__ "dquot_6.5.1" #define __DQUOT_NUM_VERSION__ 6*10000+5*100+1 -/* Size of blocks in which are counted size limits */ -#define QUOTABLOCK_BITS 10 -#define QUOTABLOCK_SIZE (1 << QUOTABLOCK_BITS) - -/* Conversion routines from and to quota blocks */ -#define qb2kb(x) ((x) << (QUOTABLOCK_BITS-10)) -#define kb2qb(x) ((x) >> (QUOTABLOCK_BITS-10)) -#define toqb(x) (((x) + QUOTABLOCK_SIZE - 1) >> QUOTABLOCK_BITS) - #define MAXQUOTAS 2 #define USRQUOTA 0 /* element used for user quotas */ #define GRPQUOTA 1 /* element used for group quotas */ @@ -80,6 +71,11 @@ #define Q_GETQUOTA 0x800007 /* get user quota structure */ #define Q_SETQUOTA 0x800008 /* set user quota structure */ +/* Size of block in which space limits are passed through the quota + * interface */ +#define QIF_DQBLKSIZE_BITS 10 +#define QIF_DQBLKSIZE (1 << QIF_DQBLKSIZE_BITS) + /* * Quota structure used for communication with userspace via quotactl * Following flags are used to specify which fields are valid @@ -187,12 +183,12 @@ extern spinlock_t dq_data_lock; * Data for one user/group kept in memory */ struct mem_dqblk { - __u32 dqb_bhardlimit; /* absolute limit on disk blks alloc */ - __u32 dqb_bsoftlimit; /* preferred limit on disk blks */ + qsize_t dqb_bhardlimit; /* absolute limit on disk blks alloc */ + qsize_t dqb_bsoftlimit; /* preferred limit on disk blks */ qsize_t dqb_curspace; /* current used space */ - __u32 dqb_ihardlimit; /* absolute limit on allocated inodes */ - __u32 dqb_isoftlimit; /* preferred inode limit */ - __u32 dqb_curinodes; /* current # allocated inodes */ + qsize_t dqb_ihardlimit; /* absolute limit on allocated inodes */ + qsize_t dqb_isoftlimit; /* preferred inode limit */ + qsize_t dqb_curinodes; /* current # allocated inodes */ time_t dqb_btime; /* time limit for excessive disk use */ time_t dqb_itime; /* time limit for excessive inode use */ }; @@ -287,9 +283,9 @@ struct dquot_operations { int (*initialize) (struct inode *, int); int (*drop) (struct inode *); int (*alloc_space) (struct inode *, qsize_t, int); - int (*alloc_inode) (const struct inode *, unsigned long); + int (*alloc_inode) (const struct inode *, qsize_t); int (*free_space) (struct inode *, qsize_t); - int (*free_inode) (const struct inode *, unsigned long); + int (*free_inode) (const struct inode *, qsize_t); int (*transfer) (struct inode *, struct iattr *); int (*write_dquot) (struct dquot *); /* Ordinary dquot write */ struct dquot *(*alloc_dquot)(struct super_block *, int); /* Allocate memory for new dquot */ diff --git a/include/linux/quotaops.h b/include/linux/quotaops.h index a558a4c1d35a..adcc7ba3accb 100644 --- a/include/linux/quotaops.h +++ b/include/linux/quotaops.h @@ -26,10 +26,10 @@ int dquot_initialize(struct inode *inode, int type); int dquot_drop(struct inode *inode); int dquot_alloc_space(struct inode *inode, qsize_t number, int prealloc); -int dquot_alloc_inode(const struct inode *inode, unsigned long number); +int dquot_alloc_inode(const struct inode *inode, qsize_t number); int dquot_free_space(struct inode *inode, qsize_t number); -int dquot_free_inode(const struct inode *inode, unsigned long number); +int dquot_free_inode(const struct inode *inode, qsize_t number); int dquot_transfer(struct inode *inode, struct iattr *iattr); int dquot_commit(struct dquot *dquot); -- cgit v1.2.2 From e4bc7b4b7ff783779b6928d55a9308910bf180a3 Mon Sep 17 00:00:00 2001 From: Jan Kara Date: Wed, 20 Aug 2008 16:21:01 +0200 Subject: quota: Make _SUSPENDED just a flag Upto now, DQUOT_USR_SUSPENDED behaved like a state - i.e., either quota was enabled or suspended or none. Now allowed states are 0, ENABLED, ENABLED | SUSPENDED. This will be useful later when we implement separate enabling of quota usage tracking and limits enforcement because we need to keep track of a state which has been suspended. Signed-off-by: Jan Kara Signed-off-by: Mark Fasheh --- include/linux/quotaops.h | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) (limited to 'include/linux') diff --git a/include/linux/quotaops.h b/include/linux/quotaops.h index adcc7ba3accb..ffd97071cd1e 100644 --- a/include/linux/quotaops.h +++ b/include/linux/quotaops.h @@ -67,8 +67,10 @@ static inline struct mem_dqinfo *sb_dqinfo(struct super_block *sb, int type) static inline int sb_has_quota_enabled(struct super_block *sb, int type) { if (type == USRQUOTA) - return sb_dqopt(sb)->flags & DQUOT_USR_ENABLED; - return sb_dqopt(sb)->flags & DQUOT_GRP_ENABLED; + return (sb_dqopt(sb)->flags & DQUOT_USR_ENABLED) + && !(sb_dqopt(sb)->flags & DQUOT_USR_SUSPENDED); + return (sb_dqopt(sb)->flags & DQUOT_GRP_ENABLED) + && !(sb_dqopt(sb)->flags & DQUOT_GROUP_SUSPENDED); } static inline int sb_any_quota_enabled(struct super_block *sb) -- cgit v1.2.2 From f55abc0fb9c3189de3da829adf3220322c0da43e Mon Sep 17 00:00:00 2001 From: Jan Kara Date: Wed, 20 Aug 2008 17:50:32 +0200 Subject: quota: Allow to separately enable quota accounting and enforcing limits Split DQUOT_USR_ENABLED (and DQUOT_GRP_ENABLED) into DQUOT_USR_USAGE_ENABLED and DQUOT_USR_LIMITS_ENABLED. This way we are able to separately enable / disable whether we should: 1) ignore quotas completely 2) just keep uptodate information about usage 3) actually enforce quota limits This is going to be useful when quota is treated as filesystem metadata - we then want to keep quota information uptodate all the time and just enable / disable limits enforcement. Signed-off-by: Jan Kara Signed-off-by: Mark Fasheh --- include/linux/quota.h | 30 +++++++++++++--- include/linux/quotaops.h | 91 +++++++++++++++++++++++++++++++++++++----------- 2 files changed, 97 insertions(+), 24 deletions(-) (limited to 'include/linux') diff --git a/include/linux/quota.h b/include/linux/quota.h index 9ea468363f9f..93717abcd35b 100644 --- a/include/linux/quota.h +++ b/include/linux/quota.h @@ -318,12 +318,34 @@ struct quota_format_type { struct quota_format_type *qf_next; }; -#define DQUOT_USR_ENABLED 0x01 /* User diskquotas enabled */ -#define DQUOT_GRP_ENABLED 0x02 /* Group diskquotas enabled */ -#define DQUOT_USR_SUSPENDED 0x04 /* User diskquotas are off, but +/* Quota state flags - they actually come in two flavors - for users and groups */ +enum { + _DQUOT_USAGE_ENABLED = 0, /* Track disk usage for users */ + _DQUOT_LIMITS_ENABLED, /* Enforce quota limits for users */ + _DQUOT_SUSPENDED, /* User diskquotas are off, but * we have necessary info in * memory to turn them on */ -#define DQUOT_GRP_SUSPENDED 0x08 /* The same for group quotas */ + _DQUOT_STATE_FLAGS +}; +#define DQUOT_USAGE_ENABLED (1 << _DQUOT_USAGE_ENABLED) +#define DQUOT_LIMITS_ENABLED (1 << _DQUOT_LIMITS_ENABLED) +#define DQUOT_SUSPENDED (1 << _DQUOT_SUSPENDED) +#define DQUOT_STATE_FLAGS (DQUOT_USAGE_ENABLED | DQUOT_LIMITS_ENABLED | \ + DQUOT_SUSPENDED) + +static inline unsigned int dquot_state_flag(unsigned int flags, int type) +{ + if (type == USRQUOTA) + return flags; + return flags << _DQUOT_STATE_FLAGS; +} + +static inline unsigned int dquot_generic_flag(unsigned int flags, int type) +{ + if (type == USRQUOTA) + return flags; + return flags >> _DQUOT_STATE_FLAGS; +} struct quota_info { unsigned int flags; /* Flags for diskquotas on this device */ diff --git a/include/linux/quotaops.h b/include/linux/quotaops.h index ffd97071cd1e..3b3346fa657c 100644 --- a/include/linux/quotaops.h +++ b/include/linux/quotaops.h @@ -40,11 +40,14 @@ int dquot_mark_dquot_dirty(struct dquot *dquot); int vfs_quota_on(struct super_block *sb, int type, int format_id, char *path, int remount); +int vfs_quota_enable(struct inode *inode, int type, int format_id, + unsigned int flags); int vfs_quota_on_path(struct super_block *sb, int type, int format_id, struct path *path); int vfs_quota_on_mount(struct super_block *sb, char *qf_name, int format_id, int type); int vfs_quota_off(struct super_block *sb, int type, int remount); +int vfs_quota_disable(struct super_block *sb, int type, unsigned int flags); int vfs_quota_sync(struct super_block *sb, int type); int vfs_get_dqinfo(struct super_block *sb, int type, struct if_dqinfo *ii); int vfs_set_dqinfo(struct super_block *sb, int type, struct if_dqinfo *ii); @@ -64,26 +67,22 @@ static inline struct mem_dqinfo *sb_dqinfo(struct super_block *sb, int type) * Functions for checking status of quota */ -static inline int sb_has_quota_enabled(struct super_block *sb, int type) +static inline int sb_has_quota_usage_enabled(struct super_block *sb, int type) { - if (type == USRQUOTA) - return (sb_dqopt(sb)->flags & DQUOT_USR_ENABLED) - && !(sb_dqopt(sb)->flags & DQUOT_USR_SUSPENDED); - return (sb_dqopt(sb)->flags & DQUOT_GRP_ENABLED) - && !(sb_dqopt(sb)->flags & DQUOT_GROUP_SUSPENDED); + return sb_dqopt(sb)->flags & + dquot_state_flag(DQUOT_USAGE_ENABLED, type); } -static inline int sb_any_quota_enabled(struct super_block *sb) +static inline int sb_has_quota_limits_enabled(struct super_block *sb, int type) { - return sb_has_quota_enabled(sb, USRQUOTA) || - sb_has_quota_enabled(sb, GRPQUOTA); + return sb_dqopt(sb)->flags & + dquot_state_flag(DQUOT_LIMITS_ENABLED, type); } static inline int sb_has_quota_suspended(struct super_block *sb, int type) { - if (type == USRQUOTA) - return sb_dqopt(sb)->flags & DQUOT_USR_SUSPENDED; - return sb_dqopt(sb)->flags & DQUOT_GRP_SUSPENDED; + return sb_dqopt(sb)->flags & + dquot_state_flag(DQUOT_SUSPENDED, type); } static inline int sb_any_quota_suspended(struct super_block *sb) @@ -92,6 +91,34 @@ static inline int sb_any_quota_suspended(struct super_block *sb) sb_has_quota_suspended(sb, GRPQUOTA); } +/* Does kernel know about any quota information for given sb + type? */ +static inline int sb_has_quota_loaded(struct super_block *sb, int type) +{ + /* Currently if anything is on, then quota usage is on as well */ + return sb_has_quota_usage_enabled(sb, type); +} + +static inline int sb_any_quota_loaded(struct super_block *sb) +{ + return sb_has_quota_loaded(sb, USRQUOTA) || + sb_has_quota_loaded(sb, GRPQUOTA); +} + +static inline int sb_has_quota_active(struct super_block *sb, int type) +{ + return sb_has_quota_loaded(sb, type) && + !sb_has_quota_suspended(sb, type); +} + +static inline int sb_any_quota_active(struct super_block *sb) +{ + return sb_has_quota_active(sb, USRQUOTA) || + sb_has_quota_active(sb, GRPQUOTA); +} + +/* For backward compatibility until we remove all users */ +#define sb_any_quota_enabled(sb) sb_any_quota_active(sb) + /* * Operations supported for diskquotas. */ @@ -106,7 +133,7 @@ extern struct quotactl_ops vfs_quotactl_ops; static inline void vfs_dq_init(struct inode *inode) { BUG_ON(!inode->i_sb); - if (sb_any_quota_enabled(inode->i_sb) && !IS_NOQUOTA(inode)) + if (sb_any_quota_active(inode->i_sb) && !IS_NOQUOTA(inode)) inode->i_sb->dq_op->initialize(inode, -1); } @@ -114,7 +141,7 @@ static inline void vfs_dq_init(struct inode *inode) * a transaction (deadlocks possible otherwise) */ static inline int vfs_dq_prealloc_space_nodirty(struct inode *inode, qsize_t nr) { - if (sb_any_quota_enabled(inode->i_sb)) { + if (sb_any_quota_active(inode->i_sb)) { /* Used space is updated in alloc_space() */ if (inode->i_sb->dq_op->alloc_space(inode, nr, 1) == NO_QUOTA) return 1; @@ -134,7 +161,7 @@ static inline int vfs_dq_prealloc_space(struct inode *inode, qsize_t nr) static inline int vfs_dq_alloc_space_nodirty(struct inode *inode, qsize_t nr) { - if (sb_any_quota_enabled(inode->i_sb)) { + if (sb_any_quota_active(inode->i_sb)) { /* Used space is updated in alloc_space() */ if (inode->i_sb->dq_op->alloc_space(inode, nr, 0) == NO_QUOTA) return 1; @@ -154,7 +181,7 @@ static inline int vfs_dq_alloc_space(struct inode *inode, qsize_t nr) static inline int vfs_dq_alloc_inode(struct inode *inode) { - if (sb_any_quota_enabled(inode->i_sb)) { + if (sb_any_quota_active(inode->i_sb)) { vfs_dq_init(inode); if (inode->i_sb->dq_op->alloc_inode(inode, 1) == NO_QUOTA) return 1; @@ -164,7 +191,7 @@ static inline int vfs_dq_alloc_inode(struct inode *inode) static inline void vfs_dq_free_space_nodirty(struct inode *inode, qsize_t nr) { - if (sb_any_quota_enabled(inode->i_sb)) + if (sb_any_quota_active(inode->i_sb)) inode->i_sb->dq_op->free_space(inode, nr); else inode_sub_bytes(inode, nr); @@ -178,7 +205,7 @@ static inline void vfs_dq_free_space(struct inode *inode, qsize_t nr) static inline void vfs_dq_free_inode(struct inode *inode) { - if (sb_any_quota_enabled(inode->i_sb)) + if (sb_any_quota_active(inode->i_sb)) inode->i_sb->dq_op->free_inode(inode, 1); } @@ -199,12 +226,12 @@ static inline int vfs_dq_off(struct super_block *sb, int remount) #else -static inline int sb_has_quota_enabled(struct super_block *sb, int type) +static inline int sb_has_quota_usage_enabled(struct super_block *sb, int type) { return 0; } -static inline int sb_any_quota_enabled(struct super_block *sb) +static inline int sb_has_quota_limits_enabled(struct super_block *sb, int type) { return 0; } @@ -219,6 +246,30 @@ static inline int sb_any_quota_suspended(struct super_block *sb) return 0; } +/* Does kernel know about any quota information for given sb + type? */ +static inline int sb_has_quota_loaded(struct super_block *sb, int type) +{ + return 0; +} + +static inline int sb_any_quota_loaded(struct super_block *sb) +{ + return 0; +} + +static inline int sb_has_quota_active(struct super_block *sb, int type) +{ + return 0; +} + +static inline int sb_any_quota_active(struct super_block *sb) +{ + return 0; +} + +/* For backward compatibility until we remove all users */ +#define sb_any_quota_enabled(sb) sb_any_quota_active(sb) + /* * NO-OP when quota not configured. */ -- cgit v1.2.2 From dcb30695f2cac86b71417629a6fe8042b4fe2ab2 Mon Sep 17 00:00:00 2001 From: Jan Kara Date: Wed, 20 Aug 2008 18:30:40 +0200 Subject: quota: Remove compatibility function sb_any_quota_enabled() Signed-off-by: Jan Kara Signed-off-by: Mark Fasheh --- include/linux/quotaops.h | 6 ------ 1 file changed, 6 deletions(-) (limited to 'include/linux') diff --git a/include/linux/quotaops.h b/include/linux/quotaops.h index 3b3346fa657c..e840ca523175 100644 --- a/include/linux/quotaops.h +++ b/include/linux/quotaops.h @@ -116,9 +116,6 @@ static inline int sb_any_quota_active(struct super_block *sb) sb_has_quota_active(sb, GRPQUOTA); } -/* For backward compatibility until we remove all users */ -#define sb_any_quota_enabled(sb) sb_any_quota_active(sb) - /* * Operations supported for diskquotas. */ @@ -267,9 +264,6 @@ static inline int sb_any_quota_active(struct super_block *sb) return 0; } -/* For backward compatibility until we remove all users */ -#define sb_any_quota_enabled(sb) sb_any_quota_active(sb) - /* * NO-OP when quota not configured. */ -- cgit v1.2.2 From ca785ec66b991e9ca74dd9840fc014487ad095e1 Mon Sep 17 00:00:00 2001 From: Jan Kara Date: Tue, 30 Sep 2008 17:53:37 +0200 Subject: quota: Introduce DQUOT_QUOTA_SYS_FILE flag If filesystem can handle quota files as system files hidden from users, we can skip a lot of cache invalidation, syncing, inode flags setting etc. when turning quotas on, off and quota_sync. Allow filesystem to indicate that it is hiding quota files from users by DQUOT_QUOTA_SYS_FILE flag. Signed-off-by: Jan Kara Signed-off-by: Mark Fasheh --- include/linux/quota.h | 7 +++++++ 1 file changed, 7 insertions(+) (limited to 'include/linux') diff --git a/include/linux/quota.h b/include/linux/quota.h index 93717abcd35b..80b8807b4988 100644 --- a/include/linux/quota.h +++ b/include/linux/quota.h @@ -332,6 +332,13 @@ enum { #define DQUOT_SUSPENDED (1 << _DQUOT_SUSPENDED) #define DQUOT_STATE_FLAGS (DQUOT_USAGE_ENABLED | DQUOT_LIMITS_ENABLED | \ DQUOT_SUSPENDED) +/* Other quota flags */ +#define DQUOT_QUOTA_SYS_FILE (1 << 6) /* Quota file is a special + * system file and user cannot + * touch it. Filesystem is + * responsible for setting + * S_NOQUOTA, S_NOATIME flags + */ static inline unsigned int dquot_state_flag(unsigned int flags, int type) { -- cgit v1.2.2 From cf770c137122b78470a67ebd5498947869a09197 Mon Sep 17 00:00:00 2001 From: Jan Kara Date: Sun, 21 Sep 2008 23:17:53 +0200 Subject: quota: Move quotaio_v[12].h from include/linux/ to fs/ Since these include files are used only by implementation of quota formats, there's no need to have them in include/linux/. Signed-off-by: Jan Kara Signed-off-by: Mark Fasheh --- include/linux/Kbuild | 2 -- include/linux/quotaio_v1.h | 33 ------------------- include/linux/quotaio_v2.h | 79 ---------------------------------------------- 3 files changed, 114 deletions(-) delete mode 100644 include/linux/quotaio_v1.h delete mode 100644 include/linux/quotaio_v2.h (limited to 'include/linux') diff --git a/include/linux/Kbuild b/include/linux/Kbuild index 95ac82340c3b..900a787cbae9 100644 --- a/include/linux/Kbuild +++ b/include/linux/Kbuild @@ -134,8 +134,6 @@ header-y += posix_types.h header-y += ppdev.h header-y += prctl.h header-y += qnxtypes.h -header-y += quotaio_v1.h -header-y += quotaio_v2.h header-y += radeonfb.h header-y += raw.h header-y += resource.h diff --git a/include/linux/quotaio_v1.h b/include/linux/quotaio_v1.h deleted file mode 100644 index 746654b5de70..000000000000 --- a/include/linux/quotaio_v1.h +++ /dev/null @@ -1,33 +0,0 @@ -#ifndef _LINUX_QUOTAIO_V1_H -#define _LINUX_QUOTAIO_V1_H - -#include - -/* - * The following constants define the amount of time given a user - * before the soft limits are treated as hard limits (usually resulting - * in an allocation failure). The timer is started when the user crosses - * their soft limit, it is reset when they go below their soft limit. - */ -#define MAX_IQ_TIME 604800 /* (7*24*60*60) 1 week */ -#define MAX_DQ_TIME 604800 /* (7*24*60*60) 1 week */ - -/* - * The following structure defines the format of the disk quota file - * (as it appears on disk) - the file is an array of these structures - * indexed by user or group number. - */ -struct v1_disk_dqblk { - __u32 dqb_bhardlimit; /* absolute limit on disk blks alloc */ - __u32 dqb_bsoftlimit; /* preferred limit on disk blks */ - __u32 dqb_curblocks; /* current block count */ - __u32 dqb_ihardlimit; /* absolute limit on allocated inodes */ - __u32 dqb_isoftlimit; /* preferred inode limit */ - __u32 dqb_curinodes; /* current # allocated inodes */ - time_t dqb_btime; /* time limit for excessive disk use */ - time_t dqb_itime; /* time limit for excessive inode use */ -}; - -#define v1_dqoff(UID) ((loff_t)((UID) * sizeof (struct v1_disk_dqblk))) - -#endif /* _LINUX_QUOTAIO_V1_H */ diff --git a/include/linux/quotaio_v2.h b/include/linux/quotaio_v2.h deleted file mode 100644 index 303d7cbe30d4..000000000000 --- a/include/linux/quotaio_v2.h +++ /dev/null @@ -1,79 +0,0 @@ -/* - * Definitions of structures for vfsv0 quota format - */ - -#ifndef _LINUX_QUOTAIO_V2_H -#define _LINUX_QUOTAIO_V2_H - -#include -#include - -/* - * Definitions of magics and versions of current quota files - */ -#define V2_INITQMAGICS {\ - 0xd9c01f11, /* USRQUOTA */\ - 0xd9c01927 /* GRPQUOTA */\ -} - -#define V2_INITQVERSIONS {\ - 0, /* USRQUOTA */\ - 0 /* GRPQUOTA */\ -} - -/* - * The following structure defines the format of the disk quota file - * (as it appears on disk) - the file is a radix tree whose leaves point - * to blocks of these structures. - */ -struct v2_disk_dqblk { - __le32 dqb_id; /* id this quota applies to */ - __le32 dqb_ihardlimit; /* absolute limit on allocated inodes */ - __le32 dqb_isoftlimit; /* preferred inode limit */ - __le32 dqb_curinodes; /* current # allocated inodes */ - __le32 dqb_bhardlimit; /* absolute limit on disk space (in QUOTABLOCK_SIZE) */ - __le32 dqb_bsoftlimit; /* preferred limit on disk space (in QUOTABLOCK_SIZE) */ - __le64 dqb_curspace; /* current space occupied (in bytes) */ - __le64 dqb_btime; /* time limit for excessive disk use */ - __le64 dqb_itime; /* time limit for excessive inode use */ -}; - -/* - * Here are header structures as written on disk and their in-memory copies - */ -/* First generic header */ -struct v2_disk_dqheader { - __le32 dqh_magic; /* Magic number identifying file */ - __le32 dqh_version; /* File version */ -}; - -/* Header with type and version specific information */ -struct v2_disk_dqinfo { - __le32 dqi_bgrace; /* Time before block soft limit becomes hard limit */ - __le32 dqi_igrace; /* Time before inode soft limit becomes hard limit */ - __le32 dqi_flags; /* Flags for quotafile (DQF_*) */ - __le32 dqi_blocks; /* Number of blocks in file */ - __le32 dqi_free_blk; /* Number of first free block in the list */ - __le32 dqi_free_entry; /* Number of block with at least one free entry */ -}; - -/* - * Structure of header of block with quota structures. It is padded to 16 bytes so - * there will be space for exactly 21 quota-entries in a block - */ -struct v2_disk_dqdbheader { - __le32 dqdh_next_free; /* Number of next block with free entry */ - __le32 dqdh_prev_free; /* Number of previous block with free entry */ - __le16 dqdh_entries; /* Number of valid entries in block */ - __le16 dqdh_pad1; - __le32 dqdh_pad2; -}; - -#define V2_DQINFOOFF sizeof(struct v2_disk_dqheader) /* Offset of info header in file */ -#define V2_DQBLKSIZE_BITS 10 -#define V2_DQBLKSIZE (1 << V2_DQBLKSIZE_BITS) /* Size of block with quota structures */ -#define V2_DQTREEOFF 1 /* Offset of tree in file in blocks */ -#define V2_DQTREEDEPTH 4 /* Depth of quota tree */ -#define V2_DQSTRINBLK ((V2_DQBLKSIZE - sizeof(struct v2_disk_dqdbheader)) / sizeof(struct v2_disk_dqblk)) /* Number of entries in one blocks */ - -#endif /* _LINUX_QUOTAIO_V2_H */ -- cgit v1.2.2 From 1ccd14b9c271c1ac6eec5c5ec5def433100e7248 Mon Sep 17 00:00:00 2001 From: Jan Kara Date: Mon, 22 Sep 2008 05:54:49 +0200 Subject: quota: Split off quota tree handling into a separate file There is going to be a new version of quota format having 64-bit quota limits and a new quota format for OCFS2. They are both going to use the same tree structure as VFSv0 quota format. So split out tree handling into a separate file and make size of leaf blocks, amount of space usable in each block (needed for checksumming) and structures contained in them configurable so that the code can be shared. Signed-off-by: Jan Kara Signed-off-by: Mark Fasheh --- include/linux/dqblk_qtree.h | 56 +++++++++++++++++++++++++++++++++++++++++++++ include/linux/dqblk_v2.h | 19 +++++++-------- 2 files changed, 64 insertions(+), 11 deletions(-) create mode 100644 include/linux/dqblk_qtree.h (limited to 'include/linux') diff --git a/include/linux/dqblk_qtree.h b/include/linux/dqblk_qtree.h new file mode 100644 index 000000000000..82a16527b367 --- /dev/null +++ b/include/linux/dqblk_qtree.h @@ -0,0 +1,56 @@ +/* + * Definitions of structures and functions for quota formats using trie + */ + +#ifndef _LINUX_DQBLK_QTREE_H +#define _LINUX_DQBLK_QTREE_H + +#include + +/* Numbers of blocks needed for updates - we count with the smallest + * possible block size (1024) */ +#define QTREE_INIT_ALLOC 4 +#define QTREE_INIT_REWRITE 2 +#define QTREE_DEL_ALLOC 0 +#define QTREE_DEL_REWRITE 6 + +struct dquot; + +/* Operations */ +struct qtree_fmt_operations { + void (*mem2disk_dqblk)(void *disk, struct dquot *dquot); /* Convert given entry from in memory format to disk one */ + void (*disk2mem_dqblk)(struct dquot *dquot, void *disk); /* Convert given entry from disk format to in memory one */ + int (*is_id)(void *disk, struct dquot *dquot); /* Is this structure for given id? */ +}; + +/* Inmemory copy of version specific information */ +struct qtree_mem_dqinfo { + struct super_block *dqi_sb; /* Sb quota is on */ + int dqi_type; /* Quota type */ + unsigned int dqi_blocks; /* # of blocks in quota file */ + unsigned int dqi_free_blk; /* First block in list of free blocks */ + unsigned int dqi_free_entry; /* First block with free entry */ + unsigned int dqi_blocksize_bits; /* Block size of quota file */ + unsigned int dqi_entry_size; /* Size of quota entry in quota file */ + unsigned int dqi_usable_bs; /* Space usable in block for quota data */ + unsigned int dqi_qtree_depth; /* Precomputed depth of quota tree */ + struct qtree_fmt_operations *dqi_ops; /* Operations for entry manipulation */ +}; + +int qtree_write_dquot(struct qtree_mem_dqinfo *info, struct dquot *dquot); +int qtree_read_dquot(struct qtree_mem_dqinfo *info, struct dquot *dquot); +int qtree_delete_dquot(struct qtree_mem_dqinfo *info, struct dquot *dquot); +int qtree_release_dquot(struct qtree_mem_dqinfo *info, struct dquot *dquot); +int qtree_entry_unused(struct qtree_mem_dqinfo *info, char *disk); +static inline int qtree_depth(struct qtree_mem_dqinfo *info) +{ + unsigned int epb = info->dqi_usable_bs >> 2; + unsigned long long entries = epb; + int i; + + for (i = 1; entries < (1ULL << 32); i++) + entries *= epb; + return i; +} + +#endif /* _LINUX_DQBLK_QTREE_H */ diff --git a/include/linux/dqblk_v2.h b/include/linux/dqblk_v2.h index 4f853322cb7f..e5e22a787d58 100644 --- a/include/linux/dqblk_v2.h +++ b/include/linux/dqblk_v2.h @@ -1,26 +1,23 @@ /* - * Definitions of structures for vfsv0 quota format + * Definitions for vfsv0 quota format */ #ifndef _LINUX_DQBLK_V2_H #define _LINUX_DQBLK_V2_H -#include +#include -/* id numbers of quota format */ +/* Id number of quota format */ #define QFMT_VFS_V0 2 /* Numbers of blocks needed for updates */ -#define V2_INIT_ALLOC 4 -#define V2_INIT_REWRITE 2 -#define V2_DEL_ALLOC 0 -#define V2_DEL_REWRITE 6 +#define V2_INIT_ALLOC QTREE_INIT_ALLOC +#define V2_INIT_REWRITE QTREE_INIT_REWRITE +#define V2_DEL_ALLOC QTREE_DEL_ALLOC +#define V2_DEL_REWRITE QTREE_DEL_REWRITE -/* Inmemory copy of version specific information */ struct v2_mem_dqinfo { - unsigned int dqi_blocks; - unsigned int dqi_free_blk; - unsigned int dqi_free_entry; + struct qtree_mem_dqinfo i; }; #endif /* _LINUX_DQBLK_V2_H */ -- cgit v1.2.2 From e3d4d56b9715e40ded2a84d0d4fa7f3b6c58983c Mon Sep 17 00:00:00 2001 From: Jan Kara Date: Thu, 2 Oct 2008 18:44:14 +0200 Subject: quota: Convert union in mem_dqinfo to a pointer Coming quota support for OCFS2 is going to need quite a bit of additional per-sb quota information. Moreover having fs.h include all the types needed for this structure would be a pain in the a**. So remove the union from mem_dqinfo and add a private pointer for filesystem's use. Signed-off-by: Jan Kara Signed-off-by: Mark Fasheh --- include/linux/dqblk_v1.h | 4 ---- include/linux/dqblk_v2.h | 4 ---- include/linux/quota.h | 5 +---- 3 files changed, 1 insertion(+), 12 deletions(-) (limited to 'include/linux') diff --git a/include/linux/dqblk_v1.h b/include/linux/dqblk_v1.h index 57f1250d5a52..9cea901f5bba 100644 --- a/include/linux/dqblk_v1.h +++ b/include/linux/dqblk_v1.h @@ -17,8 +17,4 @@ #define V1_DEL_ALLOC 0 #define V1_DEL_REWRITE 2 -/* Special information about quotafile */ -struct v1_mem_dqinfo { -}; - #endif /* _LINUX_DQBLK_V1_H */ diff --git a/include/linux/dqblk_v2.h b/include/linux/dqblk_v2.h index e5e22a787d58..ff8af1b4bda7 100644 --- a/include/linux/dqblk_v2.h +++ b/include/linux/dqblk_v2.h @@ -16,8 +16,4 @@ #define V2_DEL_ALLOC QTREE_DEL_ALLOC #define V2_DEL_REWRITE QTREE_DEL_REWRITE -struct v2_mem_dqinfo { - struct qtree_mem_dqinfo i; -}; - #endif /* _LINUX_DQBLK_V2_H */ diff --git a/include/linux/quota.h b/include/linux/quota.h index 80b8807b4988..e51dfdc0aef0 100644 --- a/include/linux/quota.h +++ b/include/linux/quota.h @@ -208,10 +208,7 @@ struct mem_dqinfo { unsigned int dqi_igrace; qsize_t dqi_maxblimit; qsize_t dqi_maxilimit; - union { - struct v1_mem_dqinfo v1_i; - struct v2_mem_dqinfo v2_i; - } u; + void *dqi_priv; }; struct super_block; -- cgit v1.2.2 From db49d2df489f727096438706a5428115e84a3f0d Mon Sep 17 00:00:00 2001 From: Jan Kara Date: Wed, 1 Oct 2008 18:21:39 +0200 Subject: quota: Allow negative usage of space and inodes For clustered filesystems, it can happen that space / inode usage goes negative temporarily (because some node is allocating another node is freeing and they are not completely in sync). So let quota code allow this and change qsize_t so a signed type so that we don't underflow the variables. Signed-off-by: Jan Kara Signed-off-by: Mark Fasheh --- include/linux/quota.h | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) (limited to 'include/linux') diff --git a/include/linux/quota.h b/include/linux/quota.h index e51dfdc0aef0..75bf761caef2 100644 --- a/include/linux/quota.h +++ b/include/linux/quota.h @@ -168,7 +168,7 @@ enum { #include typedef __kernel_uid32_t qid_t; /* Type in which we store ids in memory */ -typedef __u64 qsize_t; /* Type in which we store sizes */ +typedef long long qsize_t; /* Type in which we store sizes */ extern spinlock_t dq_data_lock; @@ -336,6 +336,7 @@ enum { * responsible for setting * S_NOQUOTA, S_NOATIME flags */ +#define DQUOT_NEGATIVE_USAGE (1 << 7) /* Allow negative quota usage */ static inline unsigned int dquot_state_flag(unsigned int flags, int type) { -- cgit v1.2.2 From 4d59bce4f9eaf26d6d9046b56a2f1c0c7f20981d Mon Sep 17 00:00:00 2001 From: Jan Kara Date: Thu, 2 Oct 2008 16:48:10 +0200 Subject: quota: Keep which entries were set by SETQUOTA quotactl Quota in a clustered environment needs to synchronize quota information among cluster nodes. This means we have to occasionally update some information in dquot from disk / network. On the other hand we have to be careful not to overwrite changes administrator did via SETQUOTA. So indicate in dquot->dq_flags which entries have been set by SETQUOTA and quota format can clear these flags when it properly propagated the changes. Signed-off-by: Jan Kara Signed-off-by: Mark Fasheh --- include/linux/quota.h | 26 ++++++++++++++++++++------ 1 file changed, 20 insertions(+), 6 deletions(-) (limited to 'include/linux') diff --git a/include/linux/quota.h b/include/linux/quota.h index 75bf761caef2..6d98885c16da 100644 --- a/include/linux/quota.h +++ b/include/linux/quota.h @@ -80,12 +80,21 @@ * Quota structure used for communication with userspace via quotactl * Following flags are used to specify which fields are valid */ -#define QIF_BLIMITS 1 -#define QIF_SPACE 2 -#define QIF_ILIMITS 4 -#define QIF_INODES 8 -#define QIF_BTIME 16 -#define QIF_ITIME 32 +enum { + QIF_BLIMITS_B = 0, + QIF_SPACE_B, + QIF_ILIMITS_B, + QIF_INODES_B, + QIF_BTIME_B, + QIF_ITIME_B, +}; + +#define QIF_BLIMITS (1 << QIF_BLIMITS_B) +#define QIF_SPACE (1 << QIF_SPACE_B) +#define QIF_ILIMITS (1 << QIF_ILIMITS_B) +#define QIF_INODES (1 << QIF_INODES_B) +#define QIF_BTIME (1 << QIF_BTIME_B) +#define QIF_ITIME (1 << QIF_ITIME_B) #define QIF_LIMITS (QIF_BLIMITS | QIF_ILIMITS) #define QIF_USAGE (QIF_SPACE | QIF_INODES) #define QIF_TIMES (QIF_BTIME | QIF_ITIME) @@ -242,6 +251,11 @@ extern struct dqstats dqstats; #define DQ_FAKE_B 3 /* no limits only usage */ #define DQ_READ_B 4 /* dquot was read into memory */ #define DQ_ACTIVE_B 5 /* dquot is active (dquot_release not called) */ +#define DQ_LASTSET_B 6 /* Following 6 bits (see QIF_) are reserved\ + * for the mask of entries set via SETQUOTA\ + * quotactl. They are set under dq_data_lock\ + * and the quota format handling dquot can\ + * clear them when it sees fit. */ struct dquot { struct hlist_node dq_hash; /* Hash list in memory */ -- cgit v1.2.2 From 571b46e40bebb0d57130ca24c4a84dfd553adb91 Mon Sep 17 00:00:00 2001 From: Jan Kara Date: Thu, 30 Oct 2008 09:17:52 +0100 Subject: quota: Update version number Increase reported version number of quota support since quota core has changed significantly. Also remove __DQUOT_NUM_VERSION__ since nobody uses it. Signed-off-by: Jan Kara Signed-off-by: Mark Fasheh --- include/linux/quota.h | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) (limited to 'include/linux') diff --git a/include/linux/quota.h b/include/linux/quota.h index 6d98885c16da..ec82beb10424 100644 --- a/include/linux/quota.h +++ b/include/linux/quota.h @@ -36,8 +36,7 @@ #include #include -#define __DQUOT_VERSION__ "dquot_6.5.1" -#define __DQUOT_NUM_VERSION__ 6*10000+5*100+1 +#define __DQUOT_VERSION__ "dquot_6.5.2" #define MAXQUOTAS 2 #define USRQUOTA 0 /* element used for user quotas */ -- cgit v1.2.2 From 3d9ea253a0e73dccaa869888ec2ceb17ea76c810 Mon Sep 17 00:00:00 2001 From: Jan Kara Date: Fri, 10 Oct 2008 16:12:23 +0200 Subject: quota: Add helpers to allow ocfs2 specific quota initialization, freeing and recovery OCFS2 needs to peek whether quota structure is already in memory so that it can avoid expensive cluster locking in that case. Similarly when freeing dquots, it checks whether it is the last quota structure user or not. Finally, it needs to get reference to dquot structure for specified id and quota type when recovering quota file after crash. Signed-off-by: Jan Kara Signed-off-by: Mark Fasheh --- include/linux/quotaops.h | 4 ++++ 1 file changed, 4 insertions(+) (limited to 'include/linux') diff --git a/include/linux/quotaops.h b/include/linux/quotaops.h index e840ca523175..e3a10272d471 100644 --- a/include/linux/quotaops.h +++ b/include/linux/quotaops.h @@ -24,6 +24,10 @@ void sync_dquots(struct super_block *sb, int type); int dquot_initialize(struct inode *inode, int type); int dquot_drop(struct inode *inode); +int dquot_drop_locked(struct inode *inode); +struct dquot *dqget(struct super_block *sb, unsigned int id, int type); +void dqput(struct dquot *dquot); +int dquot_is_cached(struct super_block *sb, unsigned int id, int type); int dquot_alloc_space(struct inode *inode, qsize_t number, int prealloc); int dquot_alloc_inode(const struct inode *inode, qsize_t number); -- cgit v1.2.2 From 12c77527e4138bc3b17d17b0e0c909e4fc84924f Mon Sep 17 00:00:00 2001 From: Jan Kara Date: Mon, 20 Oct 2008 17:05:00 +0200 Subject: quota: Implement function for scanning active dquots OCFS2 needs to scan all active dquots once in a while and sync quota information among cluster nodes. Provide a helper function for it so that it does not have to reimplement internally a list which VFS already has. Moreover this function is probably going to be useful for other clustered filesystems if they decide to use VFS quotas. Signed-off-by: Jan Kara Signed-off-by: Mark Fasheh --- include/linux/quotaops.h | 3 +++ 1 file changed, 3 insertions(+) (limited to 'include/linux') diff --git a/include/linux/quotaops.h b/include/linux/quotaops.h index e3a10272d471..f4913948c305 100644 --- a/include/linux/quotaops.h +++ b/include/linux/quotaops.h @@ -28,6 +28,9 @@ int dquot_drop_locked(struct inode *inode); struct dquot *dqget(struct super_block *sb, unsigned int id, int type); void dqput(struct dquot *dquot); int dquot_is_cached(struct super_block *sb, unsigned int id, int type); +int dquot_scan_active(struct super_block *sb, + int (*fn)(struct dquot *dquot, unsigned long priv), + unsigned long priv); int dquot_alloc_space(struct inode *inode, qsize_t number, int prealloc); int dquot_alloc_inode(const struct inode *inode, qsize_t number); -- cgit v1.2.2 From e97fcd95a4778a8caf1980c6c72fdf68185a0838 Mon Sep 17 00:00:00 2001 From: Mark Fasheh Date: Tue, 18 Nov 2008 17:15:24 -0800 Subject: jbd2: Add BH_JBDPrivateStart Add this so that file systems using JBD2 can safely allocate unused b_state bits. In this case, we add it so that Ocfs2 can define a single bit for tracking the validation state of a buffer. Acked-by: "Theodore Ts'o" Signed-off-by: Mark Fasheh --- include/linux/jbd2.h | 1 + 1 file changed, 1 insertion(+) (limited to 'include/linux') diff --git a/include/linux/jbd2.h b/include/linux/jbd2.h index c7d106ef22e2..f36645745489 100644 --- a/include/linux/jbd2.h +++ b/include/linux/jbd2.h @@ -329,6 +329,7 @@ enum jbd_state_bits { BH_State, /* Pins most journal_head state */ BH_JournalHead, /* Pins bh->b_private and jh->b_bh */ BH_Unshadow, /* Dummy bit, for BJ_Shadow wakeup filtering */ + BH_JBDPrivateStart, /* First bit available for private use by FS */ }; BUFFER_FNS(JBD, jbd) -- cgit v1.2.2 From 5cd9d5bb86daf632a40f90e2321ea9379e42f073 Mon Sep 17 00:00:00 2001 From: Jan Kara Date: Tue, 25 Nov 2008 15:31:31 +0100 Subject: quota: Unexport dqblk_v1.h and dqblk_v2.h Unexport header files dqblk_v[12].h since except for quota format ID they don't contain information userspace should be interested in. Move ID definitions to quota.h. Signed-off-by: Jan Kara Signed-off-by: Mark Fasheh --- include/linux/Kbuild | 2 -- include/linux/dqblk_v1.h | 3 --- include/linux/dqblk_v2.h | 3 --- include/linux/quota.h | 4 ++++ 4 files changed, 4 insertions(+), 8 deletions(-) (limited to 'include/linux') diff --git a/include/linux/Kbuild b/include/linux/Kbuild index 900a787cbae9..39da666067b9 100644 --- a/include/linux/Kbuild +++ b/include/linux/Kbuild @@ -56,8 +56,6 @@ header-y += dlm_device.h header-y += dlm_netlink.h header-y += dm-ioctl.h header-y += dn.h -header-y += dqblk_v1.h -header-y += dqblk_v2.h header-y += dqblk_xfs.h header-y += efs_fs_sb.h header-y += elf-fdpic.h diff --git a/include/linux/dqblk_v1.h b/include/linux/dqblk_v1.h index 9cea901f5bba..3713a7232dd8 100644 --- a/include/linux/dqblk_v1.h +++ b/include/linux/dqblk_v1.h @@ -5,9 +5,6 @@ #ifndef _LINUX_DQBLK_V1_H #define _LINUX_DQBLK_V1_H -/* Id of quota format */ -#define QFMT_VFS_OLD 1 - /* Root squash turned on */ #define V1_DQF_RSQUASH 1 diff --git a/include/linux/dqblk_v2.h b/include/linux/dqblk_v2.h index ff8af1b4bda7..18000a542677 100644 --- a/include/linux/dqblk_v2.h +++ b/include/linux/dqblk_v2.h @@ -7,9 +7,6 @@ #include -/* Id number of quota format */ -#define QFMT_VFS_V0 2 - /* Numbers of blocks needed for updates */ #define V2_INIT_ALLOC QTREE_INIT_ALLOC #define V2_INIT_REWRITE QTREE_INIT_REWRITE diff --git a/include/linux/quota.h b/include/linux/quota.h index ec82beb10424..d72d5d84fde5 100644 --- a/include/linux/quota.h +++ b/include/linux/quota.h @@ -70,6 +70,10 @@ #define Q_GETQUOTA 0x800007 /* get user quota structure */ #define Q_SETQUOTA 0x800008 /* set user quota structure */ +/* Quota format type IDs */ +#define QFMT_VFS_OLD 1 +#define QFMT_VFS_V0 2 + /* Size of block in which space limits are passed through the quota * interface */ #define QIF_DQBLKSIZE_BITS 10 -- cgit v1.2.2 From 7d9056ba20ebed6e3937a2e23183f6117919cb00 Mon Sep 17 00:00:00 2001 From: Jan Kara Date: Tue, 25 Nov 2008 15:31:32 +0100 Subject: quota: Export dquot_alloc() and dquot_destroy() functions These are default functions for creating and destroying quota structures and they should be used from filesystems. Signed-off-by: Jan Kara Signed-off-by: Mark Fasheh --- include/linux/quotaops.h | 2 ++ 1 file changed, 2 insertions(+) (limited to 'include/linux') diff --git a/include/linux/quotaops.h b/include/linux/quotaops.h index f4913948c305..21b781a3350f 100644 --- a/include/linux/quotaops.h +++ b/include/linux/quotaops.h @@ -31,6 +31,8 @@ int dquot_is_cached(struct super_block *sb, unsigned int id, int type); int dquot_scan_active(struct super_block *sb, int (*fn)(struct dquot *dquot, unsigned long priv), unsigned long priv); +struct dquot *dquot_alloc(struct super_block *sb, int type); +void dquot_destroy(struct dquot *dquot); int dquot_alloc_space(struct inode *inode, qsize_t number, int prealloc); int dquot_alloc_inode(const struct inode *inode, qsize_t number); -- cgit v1.2.2 From e06c8227fd94ec181849ba206bf032be31c4295c Mon Sep 17 00:00:00 2001 From: Joel Becker Date: Thu, 11 Sep 2008 15:35:47 -0700 Subject: jbd2: Add buffer triggers Filesystems often to do compute intensive operation on some metadata. If this operation is repeated many times, it can be very expensive. It would be much nicer if the operation could be performed once before a buffer goes to disk. This adds triggers to jbd2 buffer heads. Just before writing a metadata buffer to the journal, jbd2 will optionally call a commit trigger associated with the buffer. If the journal is aborted, an abort trigger will be called on any dirty buffers as they are dropped from pending transactions. ocfs2 will use this feature. Initially I tried to come up with a more generic trigger that could be used for non-buffer-related events like transaction completion. It doesn't tie nicely, because the information a buffer trigger needs (specific to a journal_head) isn't the same as what a transaction trigger needs (specific to a tranaction_t or perhaps journal_t). So I implemented a buffer set, with the understanding that journal/transaction wide triggers should be implemented separately. There is only one trigger set allowed per buffer. I can't think of any reason to attach more than one set. Contrast this with a journal or transaction in which multiple places may want to watch the entire transaction separately. The trigger sets are considered static allocation from the jbd2 perspective. ocfs2 will just have one trigger set per block type, setting the same set on every bh of the same type. Signed-off-by: Joel Becker Cc: "Theodore Ts'o" Cc: Signed-off-by: Mark Fasheh --- include/linux/jbd2.h | 31 +++++++++++++++++++++++++++++++ include/linux/journal-head.h | 8 ++++++++ 2 files changed, 39 insertions(+) (limited to 'include/linux') diff --git a/include/linux/jbd2.h b/include/linux/jbd2.h index f36645745489..34456476e761 100644 --- a/include/linux/jbd2.h +++ b/include/linux/jbd2.h @@ -1008,6 +1008,35 @@ int __jbd2_journal_clean_checkpoint_list(journal_t *journal); int __jbd2_journal_remove_checkpoint(struct journal_head *); void __jbd2_journal_insert_checkpoint(struct journal_head *, transaction_t *); + +/* + * Triggers + */ + +struct jbd2_buffer_trigger_type { + /* + * Fired just before a buffer is written to the journal. + * mapped_data is a mapped buffer that is the frozen data for + * commit. + */ + void (*t_commit)(struct jbd2_buffer_trigger_type *type, + struct buffer_head *bh, void *mapped_data, + size_t size); + + /* + * Fired during journal abort for dirty buffers that will not be + * committed. + */ + void (*t_abort)(struct jbd2_buffer_trigger_type *type, + struct buffer_head *bh); +}; + +extern void jbd2_buffer_commit_trigger(struct journal_head *jh, + void *mapped_data, + struct jbd2_buffer_trigger_type *triggers); +extern void jbd2_buffer_abort_trigger(struct journal_head *jh, + struct jbd2_buffer_trigger_type *triggers); + /* Buffer IO */ extern int jbd2_journal_write_metadata_buffer(transaction_t *transaction, @@ -1046,6 +1075,8 @@ extern int jbd2_journal_extend (handle_t *, int nblocks); extern int jbd2_journal_get_write_access(handle_t *, struct buffer_head *); extern int jbd2_journal_get_create_access (handle_t *, struct buffer_head *); extern int jbd2_journal_get_undo_access(handle_t *, struct buffer_head *); +void jbd2_journal_set_triggers(struct buffer_head *, + struct jbd2_buffer_trigger_type *type); extern int jbd2_journal_dirty_metadata (handle_t *, struct buffer_head *); extern void jbd2_journal_release_buffer (handle_t *, struct buffer_head *); extern int jbd2_journal_forget (handle_t *, struct buffer_head *); diff --git a/include/linux/journal-head.h b/include/linux/journal-head.h index bb70ebb6a2d5..525aac3c97df 100644 --- a/include/linux/journal-head.h +++ b/include/linux/journal-head.h @@ -12,6 +12,8 @@ typedef unsigned int tid_t; /* Unique transaction ID */ typedef struct transaction_s transaction_t; /* Compound transaction type */ + + struct buffer_head; struct journal_head { @@ -87,6 +89,12 @@ struct journal_head { * [j_list_lock] */ struct journal_head *b_cpnext, *b_cpprev; + + /* Trigger type */ + struct jbd2_buffer_trigger_type *b_triggers; + + /* Trigger type for the committing transaction's frozen data */ + struct jbd2_buffer_trigger_type *b_frozen_triggers; }; #endif /* JOURNAL_HEAD_H_INCLUDED */ -- cgit v1.2.2 From 4c728ef583b3d82266584da5cb068294c09df31e Mon Sep 17 00:00:00 2001 From: Christoph Hellwig Date: Mon, 22 Dec 2008 21:11:15 +0100 Subject: add a vfs_fsync helper Fsync currently has a fdatawrite/fdatawait pair around the method call, and a mutex_lock/unlock of the inode mutex. All callers of fsync have to duplicate this, but we have a few and most of them don't quite get it right. This patch adds a new vfs_fsync that takes care of this. It's a little more complicated as usual as ->fsync might get a NULL file pointer and just a dentry from nfsd, but otherwise gets afile and we want to take the mapping and file operations from it when it is there. Notes on the fsync callers: - ecryptfs wasn't calling filemap_fdatawrite / filemap_fdatawait on the lower file - coda wasn't calling filemap_fdatawrite / filemap_fdatawait on the host file, and returning 0 when ->fsync was missing - shm wasn't calling either filemap_fdatawrite / filemap_fdatawait nor taking i_mutex. Now given that shared memory doesn't have disk backing not doing anything in fsync seems fine and I left it out of the vfs_fsync conversion for now, but in that case we might just not pass it through to the lower file at all but just call the no-op simple_sync_file directly. [and now actually export vfs_fsync] Signed-off-by: Christoph Hellwig Signed-off-by: Al Viro --- include/linux/fs.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'include/linux') diff --git a/include/linux/fs.h b/include/linux/fs.h index e2170ee21e18..9ad9eac9eb0c 100644 --- a/include/linux/fs.h +++ b/include/linux/fs.h @@ -1827,7 +1827,7 @@ extern int __filemap_fdatawrite_range(struct address_space *mapping, extern int filemap_fdatawrite_range(struct address_space *mapping, loff_t start, loff_t end); -extern long do_fsync(struct file *file, int datasync); +extern int vfs_fsync(struct file *file, struct dentry *dentry, int datasync); extern void sync_supers(void); extern void sync_filesystems(int wait); extern void __fsync_super(struct super_block *sb); -- cgit v1.2.2 From 4ae8978cf92a96257cd8998a49e781be83571d64 Mon Sep 17 00:00:00 2001 From: Michael Kerrisk Date: Mon, 5 Jan 2009 07:19:16 -0500 Subject: inotify: fix type errors in interfaces The problems lie in the types used for some inotify interfaces, both at the kernel level and at the glibc level. This mail addresses the kernel problem. I will follow up with some suggestions for glibc changes. For the sys_inotify_rm_watch() interface, the type of the 'wd' argument is currently 'u32', it should be '__s32' . That is Robert's suggestion, and is consistent with the other declarations of watch descriptors in the kernel source, in particular, the inotify_event structure in include/linux/inotify.h: struct inotify_event { __s32 wd; /* watch descriptor */ __u32 mask; /* watch mask */ __u32 cookie; /* cookie to synchronize two events */ __u32 len; /* length (including nulls) of name */ char name[0]; /* stub for possible name */ }; The patch makes the changes needed for inotify_rm_watch(). Signed-off-by: Michael Kerrisk Cc: Robert Love Cc: Vegard Nossum Cc: Ulrich Drepper Signed-off-by: Andrew Morton Signed-off-by: Al Viro --- include/linux/syscalls.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'include/linux') diff --git a/include/linux/syscalls.h b/include/linux/syscalls.h index 04fb47bfb920..18d0a243a7b3 100644 --- a/include/linux/syscalls.h +++ b/include/linux/syscalls.h @@ -549,7 +549,7 @@ asmlinkage long sys_inotify_init(void); asmlinkage long sys_inotify_init1(int flags); asmlinkage long sys_inotify_add_watch(int fd, const char __user *path, u32 mask); -asmlinkage long sys_inotify_rm_watch(int fd, u32 wd); +asmlinkage long sys_inotify_rm_watch(int fd, __s32 wd); asmlinkage long sys_spu_run(int fd, __u32 __user *unpc, __u32 __user *ustatus); -- cgit v1.2.2 From e8c82c2e23e3527e0c9dc195e432c16784d270fa Mon Sep 17 00:00:00 2001 From: Nick Piggin Date: Tue, 6 Jan 2009 03:05:50 +0100 Subject: mm lockless pagecache barrier fix An XFS workload showed up a bug in the lockless pagecache patch. Basically it would go into an "infinite" loop, although it would sometimes be able to break out of the loop! The reason is a missing compiler barrier in the "increment reference count unless it was zero" case of the lockless pagecache protocol in the gang lookup functions. This would cause the compiler to use a cached value of struct page pointer to retry the operation with, rather than reload it. So the page might have been removed from pagecache and freed (refcount==0) but the lookup would not correctly notice the page is no longer in pagecache, and keep attempting to increment the refcount and failing, until the page gets reallocated for something else. This isn't a data corruption because the condition will be detected if the page has been reallocated. However it can result in a lockup. Linus points out that ACCESS_ONCE is also required in that pointer load, even if it's absence is not causing a bug on our particular build. The most general way to solve this is just to put an rcu_dereference in radix_tree_deref_slot. Assembly of find_get_pages, before: .L220: movq (%rbx), %rax #* ivtmp.1162, tmp82 movq (%rax), %rdi #, prephitmp.1149 .L218: testb $1, %dil #, prephitmp.1149 jne .L217 #, testq %rdi, %rdi # prephitmp.1149 je .L203 #, cmpq $-1, %rdi #, prephitmp.1149 je .L217 #, movl 8(%rdi), %esi # ._count.counter, c testl %esi, %esi # c je .L218 #, after: .L212: movq (%rbx), %rax #* ivtmp.1109, tmp81 movq (%rax), %rdi #, ret testb $1, %dil #, ret jne .L211 #, testq %rdi, %rdi # ret je .L197 #, cmpq $-1, %rdi #, ret je .L211 #, movl 8(%rdi), %esi # ._count.counter, c testl %esi, %esi # c je .L212 #, (notice the obvious infinite loop in the first example, if page->count remains 0) Signed-off-by: Nick Piggin Reviewed-by: Paul E. McKenney Signed-off-by: Linus Torvalds --- include/linux/radix-tree.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'include/linux') diff --git a/include/linux/radix-tree.h b/include/linux/radix-tree.h index a916c6660dfa..355f6e80db0d 100644 --- a/include/linux/radix-tree.h +++ b/include/linux/radix-tree.h @@ -136,7 +136,7 @@ do { \ */ static inline void *radix_tree_deref_slot(void **pslot) { - void *ret = *pslot; + void *ret = rcu_dereference(*pslot); if (unlikely(radix_tree_is_indirect_ptr(ret))) ret = RADIX_TREE_RETRY; return ret; -- cgit v1.2.2 From 10d3bd09a3c25df114f74f7f86e1b58d070bef32 Mon Sep 17 00:00:00 2001 From: Mikulas Patocka Date: Tue, 6 Jan 2009 03:04:58 +0000 Subject: dm: consolidate target deregistration error handling Change dm_unregister_target to return void and use BUG() for error reporting. dm_unregister_target can only fail because of programming bug in the target driver. It can't fail because of user's behavior or disk errors. This patch changes unregister_target to return void and use BUG if someone tries to unregister non-registered target or unregister target that is in use. This patch removes code duplication (testing of error codes in all dm targets) and reports bugs in just one place, in dm_unregister_target. In some target drivers, these return codes were ignored, which could lead to a situation where bugs could be missed. Signed-off-by: Mikulas Patocka Signed-off-by: Alasdair G Kergon --- include/linux/device-mapper.h | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) (limited to 'include/linux') diff --git a/include/linux/device-mapper.h b/include/linux/device-mapper.h index c17fd334e574..89ff2df40240 100644 --- a/include/linux/device-mapper.h +++ b/include/linux/device-mapper.h @@ -157,8 +157,7 @@ struct dm_target { }; int dm_register_target(struct target_type *t); -int dm_unregister_target(struct target_type *t); - +void dm_unregister_target(struct target_type *t); /*----------------------------------------------------------------- * Functions for creating and manipulating mapped devices. @@ -276,6 +275,9 @@ void *dm_vcalloc(unsigned long nmemb, unsigned long elem_size); *---------------------------------------------------------------*/ #define DM_NAME "device-mapper" +#define DMCRIT(f, arg...) \ + printk(KERN_CRIT DM_NAME ": " DM_MSG_PREFIX ": " f "\n", ## arg) + #define DMERR(f, arg...) \ printk(KERN_ERR DM_NAME ": " DM_MSG_PREFIX ": " f "\n", ## arg) #define DMERR_LIMIT(f, arg...) \ -- cgit v1.2.2 From 7d76345da6ed3927c9cbf5d3f7a7021e8bba7374 Mon Sep 17 00:00:00 2001 From: Kiyoshi Ueda Date: Tue, 6 Jan 2009 03:05:07 +0000 Subject: dm request: extend target interface This patch adds the following target interfaces for request-based dm. map_rq : for mapping a request rq_end_io : for finishing a request busy : for avoiding performance regression from bio-based dm. Target can tell dm core not to map requests now, and that may help requests in the block layer queue to be bigger by I/O merging. In bio-based dm, this behavior is done by device drivers managing the block layer queue. But in request-based dm, dm core has to do that since dm core manages the block layer queue. Signed-off-by: Kiyoshi Ueda Signed-off-by: Jun'ichi Nomura Signed-off-by: Alasdair G Kergon --- include/linux/device-mapper.h | 15 +++++++++++++++ 1 file changed, 15 insertions(+) (limited to 'include/linux') diff --git a/include/linux/device-mapper.h b/include/linux/device-mapper.h index 89ff2df40240..c1ba76c7c0e5 100644 --- a/include/linux/device-mapper.h +++ b/include/linux/device-mapper.h @@ -45,6 +45,8 @@ typedef void (*dm_dtr_fn) (struct dm_target *ti); */ typedef int (*dm_map_fn) (struct dm_target *ti, struct bio *bio, union map_info *map_context); +typedef int (*dm_map_request_fn) (struct dm_target *ti, struct request *clone, + union map_info *map_context); /* * Returns: @@ -57,6 +59,9 @@ typedef int (*dm_map_fn) (struct dm_target *ti, struct bio *bio, typedef int (*dm_endio_fn) (struct dm_target *ti, struct bio *bio, int error, union map_info *map_context); +typedef int (*dm_request_endio_fn) (struct dm_target *ti, + struct request *clone, int error, + union map_info *map_context); typedef void (*dm_flush_fn) (struct dm_target *ti); typedef void (*dm_presuspend_fn) (struct dm_target *ti); @@ -75,6 +80,13 @@ typedef int (*dm_ioctl_fn) (struct dm_target *ti, unsigned int cmd, typedef int (*dm_merge_fn) (struct dm_target *ti, struct bvec_merge_data *bvm, struct bio_vec *biovec, int max_size); +/* + * Returns: + * 0: The target can handle the next I/O immediately. + * 1: The target can't handle the next I/O immediately. + */ +typedef int (*dm_busy_fn) (struct dm_target *ti); + void dm_error(const char *message); /* @@ -107,7 +119,9 @@ struct target_type { dm_ctr_fn ctr; dm_dtr_fn dtr; dm_map_fn map; + dm_map_request_fn map_rq; dm_endio_fn end_io; + dm_request_endio_fn rq_end_io; dm_flush_fn flush; dm_presuspend_fn presuspend; dm_postsuspend_fn postsuspend; @@ -117,6 +131,7 @@ struct target_type { dm_message_fn message; dm_ioctl_fn ioctl; dm_merge_fn merge; + dm_busy_fn busy; }; struct io_restrictions { -- cgit v1.2.2 From ab4c1424882be9cd70b89abf2b484add355712fa Mon Sep 17 00:00:00 2001 From: Andi Kleen Date: Tue, 6 Jan 2009 03:05:09 +0000 Subject: dm: support barriers on simple devices Implement barrier support for single device DM devices This patch implements barrier support in DM for the common case of dm linear just remapping a single underlying device. In this case we can safely pass the barrier through because there can be no reordering between devices. NB. Any DM device might cease to support barriers if it gets reconfigured so code must continue to allow for a possible -EOPNOTSUPP on every barrier bio submitted. - agk Signed-off-by: Andi Kleen Signed-off-by: Mikulas Patocka Signed-off-by: Alasdair G Kergon --- include/linux/device-mapper.h | 7 +++++++ 1 file changed, 7 insertions(+) (limited to 'include/linux') diff --git a/include/linux/device-mapper.h b/include/linux/device-mapper.h index c1ba76c7c0e5..8209e08969f9 100644 --- a/include/linux/device-mapper.h +++ b/include/linux/device-mapper.h @@ -112,7 +112,14 @@ void dm_put_device(struct dm_target *ti, struct dm_dev *d); /* * Information about a target type */ + +/* + * Target features + */ +#define DM_TARGET_SUPPORTS_BARRIERS 0x00000001 + struct target_type { + uint64_t features; const char *name; struct module *module; unsigned version[3]; -- cgit v1.2.2