From 92cbe096dfd234f8c0a7e3d70575988ed54c936e Mon Sep 17 00:00:00 2001 From: Stephan Raue Date: Wed, 12 Sep 2012 21:27:03 +0200 Subject: [PATCH] linux: update RPi patch Signed-off-by: Stephan Raue --- ...inux-3.2.28-601-RPi_support-87d5bc1.patch} | 528 +++++++++++++++--- 1 file changed, 451 insertions(+), 77 deletions(-) rename packages/linux/patches/{linux-3.2.28-601-RPi_support-78f82bc.patch => linux-3.2.28-601-RPi_support-87d5bc1.patch} (99%) diff --git a/packages/linux/patches/linux-3.2.28-601-RPi_support-78f82bc.patch b/packages/linux/patches/linux-3.2.28-601-RPi_support-87d5bc1.patch similarity index 99% rename from packages/linux/patches/linux-3.2.28-601-RPi_support-78f82bc.patch rename to packages/linux/patches/linux-3.2.28-601-RPi_support-87d5bc1.patch index b5c991e8ac..e3f3cb7747 100644 --- a/packages/linux/patches/linux-3.2.28-601-RPi_support-78f82bc.patch +++ b/packages/linux/patches/linux-3.2.28-601-RPi_support-87d5bc1.patch @@ -1,8 +1,8 @@ diff --git a/arch/arm/Kconfig b/arch/arm/Kconfig -index 987c72d..5285fbf 100644 +index 987c72d..b58af94 100644 --- a/arch/arm/Kconfig +++ b/arch/arm/Kconfig -@@ -955,6 +955,22 @@ config PLAT_SPEAR +@@ -955,6 +955,23 @@ config PLAT_SPEAR help Support for ST's SPEAr platform (SPEAr3xx, SPEAr6xx and SPEAr13xx). @@ -14,6 +14,7 @@ index 987c72d..5285fbf 100644 + select HAVE_SCHED_CLOCK + select NEED_MACH_MEMORY_H + select CLKDEV_LOOKUP ++ select ARCH_HAS_CPUFREQ + select GENERIC_CLOCKEVENTS + select ARM_ERRATA_411920 + select MACH_BCM2708 @@ -25,7 +26,7 @@ index 987c72d..5285fbf 100644 config ARCH_VT8500 bool "VIA/WonderMedia 85xx" select CPU_ARM926T -@@ -1098,6 +1114,7 @@ source "arch/arm/plat-versatile/Kconfig" +@@ -1098,6 +1115,7 @@ source "arch/arm/plat-versatile/Kconfig" source "arch/arm/mach-vt8500/Kconfig" source "arch/arm/mach-w90x900/Kconfig" @@ -618,10 +619,10 @@ index 0000000..3b8bd74 +CONFIG_LIBCRC32C=y diff --git a/arch/arm/configs/bcmrpi_defconfig b/arch/arm/configs/bcmrpi_defconfig new file mode 100644 -index 0000000..5ed9c30 +index 0000000..35c5042 --- /dev/null +++ b/arch/arm/configs/bcmrpi_defconfig -@@ -0,0 +1,907 @@ +@@ -0,0 +1,913 @@ +# CONFIG_ARM_PATCH_PHYS_VIRT is not set +CONFIG_EXPERIMENTAL=y +# CONFIG_LOCALVERSION_AUTO is not set @@ -670,6 +671,12 @@ index 0000000..5ed9c30 +CONFIG_ZBOOT_ROM_BSS=0x0 +CONFIG_CMDLINE="dwc_otg.lpm_enable=0 console=ttyAMA0,115200 kgdboc=ttyAMA0,115200 root=/dev/mmcblk0p2 rootfstype=ext3 rootwait" +CONFIG_KEXEC=y ++CONFIG_CPU_FREQ=y ++CONFIG_CPU_FREQ_STAT=m ++CONFIG_CPU_FREQ_DEFAULT_GOV_ONDEMAND=y ++CONFIG_CPU_FREQ_GOV_POWERSAVE=y ++CONFIG_CPU_FREQ_GOV_USERSPACE=y ++CONFIG_CPU_FREQ_GOV_CONSERVATIVE=y +CONFIG_CPU_IDLE=y +CONFIG_VFP=y +CONFIG_BINFMT_MISC=m @@ -2103,6 +2110,20 @@ index 207f9d6..5233d54 100644 +ENTRY(__FIQ_Branch) + mov pc, r8 +ENDPROC(__FIQ_Branch) +diff --git a/arch/arm/kernel/vmlinux.lds.S b/arch/arm/kernel/vmlinux.lds.S +index 20b3041..e952a30 100644 +--- a/arch/arm/kernel/vmlinux.lds.S ++++ b/arch/arm/kernel/vmlinux.lds.S +@@ -174,7 +174,9 @@ SECTIONS + } + #endif + ++#ifdef CONFIG_SMP + PERCPU_SECTION(32) ++#endif + + #ifdef CONFIG_XIP_KERNEL + __data_loc = ALIGN(4); /* location in binary */ diff --git a/arch/arm/mach-bcm2708/Kconfig b/arch/arm/mach-bcm2708/Kconfig new file mode 100644 index 0000000..5593167 @@ -5964,10 +5985,10 @@ index 0000000..9d41c3a + diff --git a/arch/arm/mach-bcm2708/include/mach/vcio.h b/arch/arm/mach-bcm2708/include/mach/vcio.h new file mode 100644 -index 0000000..ace4ea4 +index 0000000..7dfd14e --- /dev/null +++ b/arch/arm/mach-bcm2708/include/mach/vcio.h -@@ -0,0 +1,43 @@ +@@ -0,0 +1,108 @@ +/* + * arch/arm/mach-bcm2708/include/mach/vcio.h + * @@ -5997,18 +6018,83 @@ index 0000000..ace4ea4 +#define BCM_VCIO_DRIVER_NAME "bcm2708_vcio" + +/* Constants shared with the ARM identifying separate mailbox channels */ -+#define MBOX_CHAN_POWER 0 /* for use by the power management interface */ -+#define MBOX_CHAN_FB 1 /* for use by the frame buffer */ -+#define MBOX_CHAN_VUART 2 /* for use by the virtual UART */ -+#define MBOX_CHAN_VCHIQ 3 /* for use by the VCHIQ interface */ -+#define MBOX_CHAN_LEDS 4 /* for use by the leds interface */ -+#define MBOX_CHAN_BUTTONS 5 /* for use by the buttons interface */ -+#define MBOX_CHAN_TOUCH 6 /* for use by the touchscreen interface */ ++#define MBOX_CHAN_POWER 0 /* for use by the power management interface */ ++#define MBOX_CHAN_FB 1 /* for use by the frame buffer */ ++#define MBOX_CHAN_VCHIQ 3 /* for use by the VCHIQ interface */ +#define MBOX_CHAN_PROPERTY 8 /* for use by the property channel */ -+#define MBOX_CHAN_COUNT 9 ++#define MBOX_CHAN_COUNT 9 ++ ++/* Mailbox property tags */ ++enum { ++ VCMSG_PROPERTY_END = 0x00000000, ++ VCMSG_GET_FIRMWARE_REVISION = 0x00000001, ++ VCMSG_GET_BOARD_MODEL = 0x00010001, ++ VCMSG_GET_BOARD_REVISION = 0x00020002, ++ VCMSG_GET_BOARD_MAC_ADDRESS = 0x00020003, ++ VCMSG_GET_BOARD_SERIAL = 0x00020004, ++ VCMSG_GET_ARM_MEMORY = 0x00020005, ++ VCMSG_GET_VC_MEMORY = 0x00020006, ++ VCMSG_GET_CLOCKS = 0x00020007, ++ VCMSG_GET_COMMAND_LINE = 0x00050001, ++ VCMSG_GET_DMA_CHANNELS = 0x00060001, ++ VCMSG_GET_POWER_STATE = 0x00020001, ++ VCMSG_GET_TIMING = 0x00020002, ++ VCMSG_SET_POWER_STATE = 0x00028001, ++ VCMSG_GET_CLOCK_STATE = 0x00030001, ++ VCMSG_SET_CLOCK_STATE = 0x00038001, ++ VCMSG_GET_CLOCK_RATE = 0x00030002, ++ VCMSG_SET_CLOCK_RATE = 0x00038002, ++ VCMSG_GET_VOLTAGE = 0x00030003, ++ VCMSG_SET_VOLTAGE = 0x00038003, ++ VCMSG_GET_MAX_CLOCK = 0x00030004, ++ VCMSG_GET_MAX_VOLTAGE = 0x00030005, ++ VCMSG_GET_TEMPERATURE = 0x00030006, ++ VCMSG_GET_MIN_CLOCK = 0x00030007, ++ VCMSG_GET_MIN_VOLTAGE = 0x00030008, ++ VCMSG_GET_TURBO = 0x00030009, ++ VCMSG_SET_TURBO = 0x00038009, ++ VCMSG_SET_ALLOCATE_BUFFER = 0x00040001, ++ VCMSG_SET_RELEASE_BUFFER = 0x00048001, ++ VCMSG_SET_BLANK_SCREEN = 0x00040002, ++ VCMSG_TST_BLANK_SCREEN = 0x00044002, ++ VCMSG_GET_PHYSICAL_WIDTH_HEIGHT = 0x00040003, ++ VCMSG_TST_PHYSICAL_WIDTH_HEIGHT = 0x00044003, ++ VCMSG_SET_PHYSICAL_WIDTH_HEIGHT = 0x00048003, ++ VCMSG_GET_VIRTUAL_WIDTH_HEIGHT = 0x00040004, ++ VCMSG_TST_VIRTUAL_WIDTH_HEIGHT = 0x00044004, ++ VCMSG_SET_VIRTUAL_WIDTH_HEIGHT = 0x00048004, ++ VCMSG_GET_DEPTH = 0x00040005, ++ VCMSG_TST_DEPTH = 0x00044005, ++ VCMSG_SET_DEPTH = 0x00048005, ++ VCMSG_GET_PIXEL_ORDER = 0x00040006, ++ VCMSG_TST_PIXEL_ORDER = 0x00044006, ++ VCMSG_SET_PIXEL_ORDER = 0x00048006, ++ VCMSG_GET_ALPHA_MODE = 0x00040007, ++ VCMSG_TST_ALPHA_MODE = 0x00044007, ++ VCMSG_SET_ALPHA_MODE = 0x00048007, ++ VCMSG_GET_PITCH = 0x00040008, ++ VCMSG_TST_PITCH = 0x00044008, ++ VCMSG_SET_PITCH = 0x00048008, ++ VCMSG_GET_VIRTUAL_OFFSET = 0x00040009, ++ VCMSG_TST_VIRTUAL_OFFSET = 0x00044009, ++ VCMSG_SET_VIRTUAL_OFFSET = 0x00048009, ++ VCMSG_GET_OVERSCAN = 0x0004000a, ++ VCMSG_TST_OVERSCAN = 0x0004400a, ++ VCMSG_SET_OVERSCAN = 0x0004800a, ++ VCMSG_GET_PALETTE = 0x0004000b, ++ VCMSG_TST_PALETTE = 0x0004400b, ++ VCMSG_SET_PALETTE = 0x0004800b, ++ VCMSG_GET_LAYER = 0x0004000c, ++ VCMSG_TST_LAYER = 0x0004400c, ++ VCMSG_SET_LAYER = 0x0004800c, ++ VCMSG_GET_TRANSFORM = 0x0004000d, ++ VCMSG_TST_TRANSFORM = 0x0004400d, ++ VCMSG_SET_TRANSFORM = 0x0004800d, ++}; + +extern int /*rc*/ bcm_mailbox_read(unsigned chan, uint32_t *data28); +extern int /*rc*/ bcm_mailbox_write(unsigned chan, uint32_t data28); ++extern int /*rc*/ bcm_mailbox_property(void *data, int size); + +#endif diff --git a/arch/arm/mach-bcm2708/include/mach/vmalloc.h b/arch/arm/mach-bcm2708/include/mach/vmalloc.h @@ -6239,10 +6325,10 @@ index 0000000..256bf1a +MODULE_LICENSE("GPL"); diff --git a/arch/arm/mach-bcm2708/vc_mem.c b/arch/arm/mach-bcm2708/vc_mem.c new file mode 100644 -index 0000000..775c213 +index 0000000..ae1810c --- /dev/null +++ b/arch/arm/mach-bcm2708/vc_mem.c -@@ -0,0 +1,510 @@ +@@ -0,0 +1,499 @@ +/***************************************************************************** +* Copyright 2010 - 2011 Broadcom Corporation. All rights reserved. +* @@ -6373,44 +6459,33 @@ index 0000000..775c213 + uint32_t end_tag; /* an end identifier, should be set to NULL */ +}; + -+#define VCMSG_GET_ARM_MEMORY 0x00010005 -+#define VCMSG_GET_VC_MEMORY 0x00010006 -+ +static void vc_mem_update(void) +{ -+ uint32_t success; -+ dma_addr_t vc_mem; /* the memory address accessed from videocore */ -+ struct vc_set_msg *get_mem; /* the memory address accessed from driver */ ++ struct vc_set_msg msg; /* the memory address accessed from driver */ ++ uint32_t s; + -+ /* allocate some memory for the messages to use throughout the lifetime of the driver, use the larger of the two message structures */ -+ get_mem = (struct vc_set_msg *)dma_alloc_coherent(NULL, PAGE_ALIGN(sizeof(struct vc_set_msg)), &vc_mem, GFP_ATOMIC); -+ /* clear any garbage */ -+ memset(get_mem, 0, sizeof(struct vc_set_msg)); ++ memset(&msg, 0, sizeof msg); + /* create the message */ -+ get_mem->msg_size = sizeof(struct vc_set_msg); -+ get_mem->tag[0].tag_id = VCMSG_GET_VC_MEMORY; -+ get_mem->tag[0].buffer_size = 8; -+ get_mem->tag[0].data_size = 0; -+ get_mem->tag[1].tag_id = VCMSG_GET_ARM_MEMORY; -+ get_mem->tag[1].buffer_size = 8; -+ get_mem->tag[1].data_size = 0; ++ msg.msg_size = sizeof msg; ++ msg.tag[0].tag_id = VCMSG_GET_VC_MEMORY; ++ msg.tag[0].buffer_size = 8; ++ msg.tag[0].data_size = 0; ++ msg.tag[1].tag_id = VCMSG_GET_ARM_MEMORY; ++ msg.tag[1].buffer_size = 8; ++ msg.tag[1].data_size = 0; + + /* send the message */ -+ wmb(); -+ bcm_mailbox_write(MBOX_CHAN_PROPERTY,(uint32_t)vc_mem); -+ bcm_mailbox_read(MBOX_CHAN_PROPERTY, &success); -+ rmb(); ++ s = bcm_mailbox_property(&msg, sizeof msg); + -+ LOG_DBG("%s: resp %x, vcbase=%x vcsize=%x armbase=%x armsize=%x", __func__, get_mem->request_code, -+ get_mem->tag[0].base, get_mem->tag[0].size, get_mem->tag[1].base, get_mem->tag[1].size); ++ LOG_DBG("%s: success=%d resp %x, vcbase=%x vcsize=%x armbase=%x armsize=%x", __func__, s, msg.request_code, ++ msg.tag[0].base, msg.tag[0].size, msg.tag[1].base, msg.tag[1].size); + + /* check we're all good */ -+ if (get_mem->request_code & 0x80000000) { -+ mm_vc_mem_base = get_mem->tag[0].base; -+ mm_vc_mem_size = get_mem->tag[0].size+get_mem->tag[1].size; -+ mm_vc_mem_phys_addr = get_mem->tag[1].base; ++ if (s == 0 && msg.request_code & 0x80000000) { ++ mm_vc_mem_base = msg.tag[0].base; ++ mm_vc_mem_size = msg.tag[0].size+msg.tag[1].size; ++ mm_vc_mem_phys_addr = msg.tag[1].base; + } -+ dma_free_coherent(NULL, PAGE_ALIGN(sizeof(struct vc_set_msg)), (void *)get_mem, vc_mem); +} + + @@ -6755,10 +6830,10 @@ index 0000000..775c213 +MODULE_AUTHOR("Broadcom Corporation"); diff --git a/arch/arm/mach-bcm2708/vcio.c b/arch/arm/mach-bcm2708/vcio.c new file mode 100644 -index 0000000..3874051 +index 0000000..468fdef --- /dev/null +++ b/arch/arm/mach-bcm2708/vcio.c -@@ -0,0 +1,304 @@ +@@ -0,0 +1,338 @@ +/* + * linux/arch/arm/mach-bcm2708/vcio.c + * @@ -6977,6 +7052,40 @@ index 0000000..3874051 + mbox_dev = dev; +} + ++extern int bcm_mailbox_property(void *data, int size) ++{ ++ uint32_t success; ++ dma_addr_t mem_bus; /* the memory address accessed from videocore */ ++ void *mem_kern; /* the memory address accessed from driver */ ++ int s = 0; ++ ++ /* allocate some memory for the messages communicating with GPU */ ++ mem_kern = dma_alloc_coherent(NULL, PAGE_ALIGN(size), &mem_bus, GFP_ATOMIC); ++ if (mem_kern) { ++ /* create the message */ ++ memcpy(mem_kern, data, size); ++ ++ /* send the message */ ++ wmb(); ++ s = bcm_mailbox_write(MBOX_CHAN_PROPERTY, (uint32_t)mem_bus); ++ if (s == 0) { ++ s = bcm_mailbox_read(MBOX_CHAN_PROPERTY, &success); ++ } ++ if (s == 0) { ++ /* copy the response */ ++ rmb(); ++ memcpy(data, mem_kern, size); ++ } ++ dma_free_coherent(NULL, PAGE_ALIGN(size), mem_kern, mem_bus); ++ } else { ++ s = -ENOMEM; ++ } ++ if (s != 0) ++ printk(KERN_ERR DRIVER_NAME ": %s failed (%d)\n", __func__, s); ++ return s; ++} ++EXPORT_SYMBOL_GPL(bcm_mailbox_property); ++ +/* ---------------------------------------------------------------------- + * Platform Device for Mailbox + * -------------------------------------------------------------------- */ @@ -7121,6 +7230,279 @@ index d061d2f..436dc2c 100644 mov pc, lr ENTRY(cpu_v6_dcache_clean_area) +diff --git a/drivers/cpufreq/Kconfig.arm b/drivers/cpufreq/Kconfig.arm +index 72a0044..c28423d 100644 +--- a/drivers/cpufreq/Kconfig.arm ++++ b/drivers/cpufreq/Kconfig.arm +@@ -30,3 +30,11 @@ config ARM_EXYNOS4210_CPUFREQ + SoC (S5PV310 or S5PC210). + + If in doubt, say N. ++ ++config ARM_BCM2835_CPUFREQ ++ bool "BCM2835 Driver" ++ default y ++ help ++ This adds the CPUFreq driver for BCM2835 ++ ++ If in doubt, say N. +diff --git a/drivers/cpufreq/Makefile b/drivers/cpufreq/Makefile +index a48bc02..51ebbb3 100644 +--- a/drivers/cpufreq/Makefile ++++ b/drivers/cpufreq/Makefile +@@ -43,6 +43,7 @@ obj-$(CONFIG_UX500_SOC_DB8500) += db8500-cpufreq.o + obj-$(CONFIG_ARM_S3C64XX_CPUFREQ) += s3c64xx-cpufreq.o + obj-$(CONFIG_ARM_S5PV210_CPUFREQ) += s5pv210-cpufreq.o + obj-$(CONFIG_ARM_EXYNOS4210_CPUFREQ) += exynos4210-cpufreq.o ++obj-$(CONFIG_ARM_BCM2835_CPUFREQ) += bcm2835-cpufreq.o + + ################################################################################## + # PowerPC platform drivers +diff --git a/drivers/cpufreq/bcm2835-cpufreq.c b/drivers/cpufreq/bcm2835-cpufreq.c +new file mode 100755 +index 0000000..aa6fc66 +--- /dev/null ++++ b/drivers/cpufreq/bcm2835-cpufreq.c +@@ -0,0 +1,239 @@ ++/***************************************************************************** ++* Copyright 2011 Broadcom Corporation. All rights reserved. ++* ++* Unless you and Broadcom execute a separate written software license ++* agreement governing use of this software, this software is licensed to you ++* under the terms of the GNU General Public License version 2, available at ++* http://www.broadcom.com/licenses/GPLv2.php (the "GPL"). ++* ++* Notwithstanding the above, under no circumstances may you combine this ++* software in any way with any other Broadcom software provided under a ++* license other than the GPL, without Broadcom's express prior written ++* consent. ++*****************************************************************************/ ++ ++/***************************************************************************** ++* FILENAME: bcm2835-cpufreq.h ++* DESCRIPTION: This driver dynamically manages the CPU Frequency of the ARM ++* processor. Messages are sent to Videocore either setting or requesting the ++* frequency of the ARM in order to match an appropiate frequency to the current ++* usage of the processor. The policy which selects the frequency to use is ++* defined in the kernel .config file, but can be changed during runtime. ++*****************************************************************************/ ++ ++/* ---------- INCLUDES ---------- */ ++#include ++#include ++#include ++#include ++#include ++ ++/* ---------- DEFINES ---------- */ ++/*#define CPUFREQ_DEBUG_ENABLE*/ /* enable debugging */ ++#define MODULE_NAME "bcm2835-cpufreq" ++ ++#define VCMSG_ID_ARM_CLOCK 0x000000003 /* Clock/Voltage ID's */ ++ ++/* debug printk macros */ ++#ifdef CPUFREQ_DEBUG_ENABLE ++#define print_debug(fmt,...) pr_debug("%s:%s:%d: "fmt, MODULE_NAME, __func__, __LINE__, ##__VA_ARGS__) ++#else ++#define print_debug(fmt,...) ++#endif ++#define print_err(fmt,...) pr_err("%s:%s:%d: "fmt, MODULE_NAME, __func__,__LINE__, ##__VA_ARGS__) ++#define print_info(fmt,...) pr_info("%s: "fmt, MODULE_NAME, ##__VA_ARGS__) ++ ++/* tag part of the message */ ++struct vc_msg_tag { ++ uint32_t tag_id; /* the message id */ ++ uint32_t buffer_size; /* size of the buffer (which in this case is always 8 bytes) */ ++ uint32_t data_size; /* amount of data being sent or received */ ++ uint32_t dev_id; /* the ID of the clock/voltage to get or set */ ++ uint32_t val; /* the value (e.g. rate (in Hz)) to set */ ++}; ++ ++/* message structure to be sent to videocore */ ++struct vc_msg { ++ uint32_t msg_size; /* simply, sizeof(struct vc_msg) */ ++ uint32_t request_code; /* holds various information like the success and number of bytes returned (refer to mailboxes wiki) */ ++ struct vc_msg_tag tag; /* the tag structure above to make */ ++ uint32_t end_tag; /* an end identifier, should be set to NULL */ ++}; ++ ++/* ---------- GLOBALS ---------- */ ++static struct cpufreq_driver bcm2835_cpufreq_driver; /* the cpufreq driver global */ ++ ++/* ++ =============================================== ++ clk_rate either gets or sets the clock rates. ++ =============================================== ++*/ ++static uint32_t bcm2835_cpufreq_set_clock(int cur_rate, int arm_rate) ++{ ++ int s, actual_rate=0; ++ struct vc_msg msg; ++ ++ /* wipe all previous message data */ ++ memset(&msg, 0, sizeof msg); ++ ++ msg.msg_size = sizeof msg; ++ ++ msg.tag.tag_id = VCMSG_SET_CLOCK_RATE; ++ msg.tag.buffer_size = 8; ++ msg.tag.data_size = 8; /* we're sending the clock ID and the new rates which is a total of 2 words */ ++ msg.tag.dev_id = VCMSG_ID_ARM_CLOCK; ++ msg.tag.val = arm_rate * 1000; ++ ++ /* send the message */ ++ s = bcm_mailbox_property(&msg, sizeof msg); ++ ++ /* check if it was all ok and return the rate in KHz */ ++ if (s == 0 && (msg.request_code & 0x80000000)) ++ actual_rate = msg.tag.val/1000; ++ ++ print_debug("Setting new frequency = %d -> %d (actual %d)", cur_rate, arm_rate, actual_rate); ++ return actual_rate; ++} ++ ++static uint32_t bcm2835_cpufreq_get_clock(int tag) ++{ ++ int s; ++ int arm_rate = 0; ++ struct vc_msg msg; ++ ++ /* wipe all previous message data */ ++ memset(&msg, 0, sizeof msg); ++ ++ msg.msg_size = sizeof msg; ++ msg.tag.tag_id = tag; ++ msg.tag.buffer_size = 8; ++ msg.tag.data_size = 4; /* we're just sending the clock ID which is one word long */ ++ msg.tag.dev_id = VCMSG_ID_ARM_CLOCK; ++ ++ /* send the message */ ++ s = bcm_mailbox_property(&msg, sizeof msg); ++ ++ /* check if it was all ok and return the rate in KHz */ ++ if (s == 0 && (msg.request_code & 0x80000000)) ++ arm_rate = msg.tag.val/1000; ++ ++ print_debug("%s frequency = %d", ++ tag == VCMSG_GET_CLOCK_RATE ? "Current": ++ tag == VCMSG_GET_MIN_CLOCK ? "Min": ++ tag == VCMSG_GET_MAX_CLOCK ? "Max": ++ "Unexpected", arm_rate); ++ ++ return arm_rate; ++} ++ ++/* ++ ==================================================== ++ Module Initialisation registers the cpufreq driver ++ ==================================================== ++*/ ++static int __init bcm2835_cpufreq_module_init(void) ++{ ++ print_debug("IN"); ++ return cpufreq_register_driver(&bcm2835_cpufreq_driver); ++} ++ ++/* ++ ============= ++ Module exit ++ ============= ++*/ ++static void __exit bcm2835_cpufreq_module_exit(void) ++{ ++ print_debug("IN"); ++ cpufreq_unregister_driver(&bcm2835_cpufreq_driver); ++ return; ++} ++ ++/* ++ ============================================================== ++ Initialisation function sets up the CPU policy for first use ++ ============================================================== ++*/ ++static int bcm2835_cpufreq_driver_init(struct cpufreq_policy *policy) ++{ ++ /* measured value of how long it takes to change frequency */ ++ policy->cpuinfo.transition_latency = 355000; /* ns */ ++ ++ /* now find out what the maximum and minimum frequencies are */ ++ policy->min = policy->cpuinfo.min_freq = bcm2835_cpufreq_get_clock(VCMSG_GET_MIN_CLOCK); ++ policy->max = policy->cpuinfo.max_freq = bcm2835_cpufreq_get_clock(VCMSG_GET_MAX_CLOCK); ++ policy->cur = bcm2835_cpufreq_get_clock(VCMSG_GET_CLOCK_RATE); ++ ++ print_info("min=%d max=%d cur=%d", policy->min, policy->max, policy->cur); ++ return 0; ++} ++ ++/* ++ ================================================================================= ++ Target function chooses the most appropriate frequency from the table to enable ++ ================================================================================= ++*/ ++ ++static int bcm2835_cpufreq_driver_target(struct cpufreq_policy *policy, unsigned int target_freq, unsigned int relation) ++{ ++ unsigned int target = target_freq; ++ unsigned int cur = policy->cur; ++ print_debug("%s: min=%d max=%d cur=%d target=%d",policy->governor->name,policy->min,policy->max,policy->cur,target_freq); ++ ++ /* if we are above min and using ondemand, then just use max */ ++ if (strcmp("ondemand", policy->governor->name)==0 && target > policy->min) ++ target = policy->max; ++ /* if the frequency is the same, just quit */ ++ if (target == policy->cur) ++ return 0; ++ ++ /* otherwise were good to set the clock frequency */ ++ policy->cur = bcm2835_cpufreq_set_clock(policy->cur, target); ++ ++ if (!policy->cur) ++ { ++ print_err("Error occurred setting a new frequency (%d)!", target); ++ policy->cur = bcm2835_cpufreq_get_clock(VCMSG_GET_CLOCK_RATE); ++ return -EINVAL; ++ } ++ print_info("Freq %d->%d (min=%d max=%d target=%d request=%d)", cur, policy->cur, policy->min, policy->max, target_freq, target); ++ return 0; ++} ++ ++static unsigned int bcm2835_cpufreq_driver_get(unsigned int cpu) ++{ ++ unsigned int actual_rate = bcm2835_cpufreq_get_clock(VCMSG_GET_CLOCK_RATE); ++ print_debug("%d", actual_rate); ++ return actual_rate; ++} ++ ++/* ++ ================================================================================= ++ Verify ensures that when a policy is changed, it is suitable for the CPU to use ++ ================================================================================= ++*/ ++ ++static int bcm2835_cpufreq_driver_verify(struct cpufreq_policy *policy) ++{ ++ print_info("switching to governor %s", policy->governor->name); ++ return 0; ++} ++ ++ ++/* the CPUFreq driver */ ++static struct cpufreq_driver bcm2835_cpufreq_driver = { ++ .name = "BCM2835 CPUFreq", ++ .owner = THIS_MODULE, ++ .init = bcm2835_cpufreq_driver_init, ++ .verify = bcm2835_cpufreq_driver_verify, ++ .target = bcm2835_cpufreq_driver_target, ++ .get = bcm2835_cpufreq_driver_get ++}; ++ ++MODULE_AUTHOR("Dorian Peake and Dom Cobley"); ++MODULE_DESCRIPTION("CPU frequency driver for BCM2835 chip"); ++MODULE_LICENSE("GPL"); ++ ++module_init(bcm2835_cpufreq_module_init); ++module_exit(bcm2835_cpufreq_module_exit); ++ diff --git a/drivers/i2c/busses/Kconfig b/drivers/i2c/busses/Kconfig index a3afac4..cbc62ff 100644 --- a/drivers/i2c/busses/Kconfig @@ -32338,7 +32720,7 @@ index 7ca290f..802dda6 100644 obj-$(CONFIG_USB_OCTEON2_COMMON) += octeon2-common.o diff --git a/drivers/usb/host/dwc_common_port/Makefile b/drivers/usb/host/dwc_common_port/Makefile new file mode 100644 -index 0000000..203c7ea +index 0000000..63e3485 --- /dev/null +++ b/drivers/usb/host/dwc_common_port/Makefile @@ -0,0 +1,58 @@ @@ -32374,9 +32756,9 @@ index 0000000..203c7ea + +else + -+ifeq ($(KDIR),) -+$(error Must give "KDIR=/path/to/kernel/source" on command line or in environment) -+endif ++#ifeq ($(KDIR),) ++#$(error Must give "KDIR=/path/to/kernel/source" on command line or in environment) ++#endif + +ifeq ($(ARCH),) +$(error Must give "ARCH=" on command line or in environment. Also, if \ @@ -62145,7 +62527,7 @@ index 0000000..8a0e41b +#endif diff --git a/drivers/usb/host/dwc_otg/dwc_otg_hcd.c b/drivers/usb/host/dwc_otg/dwc_otg_hcd.c new file mode 100644 -index 0000000..20f989e +index 0000000..0ce7e46 --- /dev/null +++ b/drivers/usb/host/dwc_otg/dwc_otg_hcd.c @@ -0,0 +1,3478 @@ @@ -62973,6 +63355,7 @@ index 0000000..20f989e + } else if (dwc_otg_hcd->status_buf != NULL) { + DWC_FREE(dwc_otg_hcd->status_buf); + } ++ DWC_SPINLOCK_FREE(dwc_otg_hcd->channel_lock); + DWC_SPINLOCK_FREE(dwc_otg_hcd->lock); + /* Set core_if's lock pointer to NULL */ + dwc_otg_hcd->core_if->lock = NULL; @@ -62999,6 +63382,7 @@ index 0000000..20f989e + dwc_hc_t *channel; + + hcd->lock = DWC_SPINLOCK_ALLOC(); ++ hcd->channel_lock = DWC_SPINLOCK_ALLOC(); + DWC_DEBUGPL(DBG_HCDV, "init of HCD %p given core_if %p\n", + hcd, core_if); + if (!hcd->lock) { @@ -63399,7 +63783,7 @@ index 0000000..20f989e + dwc_otg_qh_t *qh; + int num_channels; + dwc_irqflags_t flags; -+ dwc_spinlock_t *channel_lock = DWC_SPINLOCK_ALLOC(); ++ dwc_spinlock_t *channel_lock = hcd->channel_lock; + dwc_otg_transaction_type_e ret_val = DWC_OTG_TRANSACTION_NONE; + +#ifdef DEBUG_SOF @@ -63499,8 +63883,6 @@ index 0000000..20f989e +#ifdef DEBUG_HOST_CHANNELS + last_sel_trans_num_avail_hc_at_end = hcd->available_host_channels; +#endif /* DEBUG_HOST_CHANNELS */ -+ -+ DWC_SPINLOCK_FREE(channel_lock); + return ret_val; +} + @@ -65629,7 +66011,7 @@ index 0000000..20f989e +#endif /* DWC_DEVICE_ONLY */ diff --git a/drivers/usb/host/dwc_otg/dwc_otg_hcd.h b/drivers/usb/host/dwc_otg/dwc_otg_hcd.h new file mode 100644 -index 0000000..dd30f47 +index 0000000..6d82127 --- /dev/null +++ b/drivers/usb/host/dwc_otg/dwc_otg_hcd.h @@ -0,0 +1,824 @@ @@ -66183,7 +66565,7 @@ index 0000000..dd30f47 + + /* */ + dwc_spinlock_t *lock; -+ ++ dwc_spinlock_t *channel_lock; + /** + * Private data that could be used by OS wrapper. + */ @@ -66459,10 +66841,10 @@ index 0000000..dd30f47 +#endif /* DWC_DEVICE_ONLY */ diff --git a/drivers/usb/host/dwc_otg/dwc_otg_hcd_ddma.c b/drivers/usb/host/dwc_otg/dwc_otg_hcd_ddma.c new file mode 100644 -index 0000000..d0d5fa1 +index 0000000..a2ceb77 --- /dev/null +++ b/drivers/usb/host/dwc_otg/dwc_otg_hcd_ddma.c -@@ -0,0 +1,1133 @@ +@@ -0,0 +1,1132 @@ +/*========================================================================== + * $File: //dwh/usb_iip/dev/software/otg/linux/drivers/dwc_otg_hcd_ddma.c $ + * $Revision: #10 $ @@ -66741,7 +67123,7 @@ index 0000000..d0d5fa1 +static void release_channel_ddma(dwc_otg_hcd_t * hcd, dwc_otg_qh_t * qh) +{ + dwc_irqflags_t flags; -+ dwc_spinlock_t *channel_lock = DWC_SPINLOCK_ALLOC(); ++ dwc_spinlock_t *channel_lock = hcd->channel_lock; + + dwc_hc_t *hc = qh->channel; + if (dwc_qh_is_non_per(qh)) { @@ -66771,7 +67153,6 @@ index 0000000..d0d5fa1 + dwc_memset(qh->desc_list, 0x00, + sizeof(dwc_otg_host_dma_desc_t) * max_desc_num(qh)); + } -+ DWC_SPINLOCK_FREE(channel_lock); +} + +/** @@ -68021,10 +68402,10 @@ index 0000000..04ca4c2 +#endif /* DWC_DEVICE_ONLY */ diff --git a/drivers/usb/host/dwc_otg/dwc_otg_hcd_intr.c b/drivers/usb/host/dwc_otg/dwc_otg_hcd_intr.c new file mode 100644 -index 0000000..f1658fa +index 0000000..21e8f09 --- /dev/null +++ b/drivers/usb/host/dwc_otg/dwc_otg_hcd_intr.c -@@ -0,0 +1,2230 @@ +@@ -0,0 +1,2229 @@ +/* ========================================================================== + * $File: //dwh/usb_iip/dev/software/otg/linux/drivers/dwc_otg_hcd_intr.c $ + * $Revision: #89 $ @@ -68949,7 +69330,7 @@ index 0000000..f1658fa + dwc_otg_transaction_type_e tr_type; + int free_qtd; + dwc_irqflags_t flags; -+ dwc_spinlock_t *channel_lock = DWC_SPINLOCK_ALLOC(); ++ dwc_spinlock_t *channel_lock = hcd->channel_lock; + + DWC_DEBUGPL(DBG_HCDV, " %s: channel %d, halt_status %d, xfer_len %d\n", + __func__, hc->hc_num, halt_status, hc->xfer_len); @@ -69036,7 +69417,6 @@ index 0000000..f1658fa + if (tr_type != DWC_OTG_TRANSACTION_NONE) { + dwc_otg_hcd_queue_transactions(hcd, tr_type); + } -+ DWC_SPINLOCK_FREE(channel_lock); +} + +/** @@ -90656,10 +91036,10 @@ index 0000000..68d838d +} diff --git a/sound/arm/bcm2835.c b/sound/arm/bcm2835.c new file mode 100755 -index 0000000..3f6b0ea +index 0000000..44bedb5 --- /dev/null +++ b/sound/arm/bcm2835.c -@@ -0,0 +1,424 @@ +@@ -0,0 +1,418 @@ +/***************************************************************************** +* Copyright 2011 Broadcom Corporation. All rights reserved. +* @@ -90749,10 +91129,7 @@ index 0000000..3f6b0ea + bcm2835_chip_t *chip; + struct snd_card *card; + int err; -+ printk(KERN_INFO "### snd_bcm2835_alsa_probe %p ###", pdev); -+ -+ printk -+ ("############ PROBING FOR bcm2835 ALSA device (%d):(%d) ###############\n", ++ printk(KERN_INFO "Probing FOR bcm2835 ALSA device (%d):(%d)\n", + dev, enable[dev]); + + if (dev >= MAX_SUBSTREAMS) @@ -90776,7 +91153,6 @@ index 0000000..3f6b0ea + strcpy(g_card->shortname, "bcm2835 ALSA"); + sprintf(g_card->longname, "%s", g_card->shortname); + -+ printk("Creating device/chip ..\n"); + err = snd_bcm2835_create(g_card, pdev, &chip); + if (err < 0) { + printk(KERN_ERR "Failed to create bcm2835 chip\n"); @@ -90790,7 +91166,6 @@ index 0000000..3f6b0ea + goto out_bcm2835_new_pcm; + } + -+ printk("Adding controls ..\n"); + err = snd_bcm2835_new_ctl(chip); + if (err < 0) { + printk(KERN_ERR "Failed to create new BCM2835 ctl\n"); @@ -90807,7 +91182,6 @@ index 0000000..3f6b0ea + chip->pdev[dev] = pdev; + + if (dev == 0) { -+ printk("Registering card ....\n"); + err = snd_card_register(card); + if (err < 0) { + printk(KERN_ERR @@ -90815,9 +91189,9 @@ index 0000000..3f6b0ea + goto out_card_register; + } + platform_set_drvdata(pdev, card); -+ printk("bcm2835 ALSA CARD CREATED!\n"); ++ printk(KERN_INFO "bcm2835 ALSA card created!\n"); + } else { -+ printk("bcm2835 ALSA CHIP CREATED!\n"); ++ printk(KERN_INFO "bcm2835 ALSA chip created!\n"); + platform_set_drvdata(pdev, (void *)dev); + } + @@ -91042,7 +91416,7 @@ index 0000000..3f6b0ea + printk("Error registering bcm2835_alsa7_driver %d .\n", err); + goto unregister_6; + } -+ printk(KERN_INFO "### BCM2835 ALSA driver init %s ### \n", ++ printk(KERN_INFO "BCM2835 ALSA driver init %s\n", + err ? "FAILED" : "OK"); + + return 0;