diff --git a/target/linux/cns3xxx/files/arch/arm/mach-cns3xxx/hydrogen.c
b/target/linux/cns3xxx/files/arch/arm/mach-cns3xxx/hydrogen.c
new file mode 100644
index 0000000..37fefff
--- /dev/null
+++ b/target/linux/cns3xxx/files/arch/arm/mach-cns3xxx/hydrogen.c
@@ -0,0 +1,363 @@
+/*
+ * Ping Communication Hydrogen
+ *
+ * Copyright 2000 Deep Blue Solutions Ltd
+ * Copyright 2008 ARM Limited
+ * Copyright 2008 Cavium Networks
+ * Scott Shu
+ * Copyright 2010 MontaVista Software, LLC.
+ * Anton Vorontsov <avoront...@mvista.com>
+ * Copyright 2012 Ping Communication
+ * Jon Suphammer <j...@suphammer.net>
+ *
+ * This file is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License, Version 2, as
+ * published by the Free Software Foundation.
+ */
+
+#include <linux/init.h>
+#include <linux/kernel.h>
+#include <linux/compiler.h>
+#include <linux/io.h>
+#include <linux/gpio.h>
+#include <linux/dma-mapping.h>
+#include <linux/serial_core.h>
+#include <linux/serial_8250.h>
+#include <linux/platform_device.h>
+#include <linux/mtd/mtd.h>
+#include <linux/mtd/physmap.h>
+#include <linux/mtd/partitions.h>
+#include <linux/leds.h>
+#include <linux/spi/spi.h>
+#include <linux/spi/flash.h>
+#include <linux/if_ether.h>
+#include <linux/etherdevice.h>
+#include <asm/setup.h>
+#include <asm/mach-types.h>
+#include <asm/mach/arch.h>
+#include <asm/mach/map.h>
+#include <asm/mach/time.h>
+#include <mach/cns3xxx.h>
+#include <mach/irqs.h>
+#include <mach/platform.h>
+#include <asm/hardware/gic.h>
+#include "core.h"
+#include "devices.h"
+
+#define ARRAY_AND_SIZE(x) (x), ARRAY_SIZE(x)
+
+static int spi_enable __initdata = 0;
+
+static int __init hydrogen_spi_enable(char *s)
+{
+ spi_enable = 1;
+ return 1;
+}
+__setup ("hydrogen_spi", hydrogen_spi_enable);
+
+
+/*
+ * NOR Flash
+ */
+static struct mtd_partition hydrogen_nor_partitions[] = {
+ {
+ .name = "uboot",
+ .size = SZ_512K,
+ .offset = 0,
+ .mask_flags = MTD_WRITEABLE,
+ }, {
+ .name = "uboot_env",
+ .size = SZ_128K,
+ .offset = MTDPART_OFS_APPEND,
+ .mask_flags = MTD_WRITEABLE,
+ }, {
+ .name = "staging",
+ .size = SZ_2M + SZ_1M,
+ .offset = MTDPART_OFS_APPEND,
+ .mask_flags = MTD_WRITEABLE,
+ }, {
+ .name = "kernel",
+ .size = SZ_2M,
+ .offset = MTDPART_OFS_APPEND,
+ }, {
+ .name = "rootfs",
+ .size = MTDPART_SIZ_FULL,
+ .offset = MTDPART_OFS_APPEND,
+ },
+};
+
+static struct physmap_flash_data hydrogen_nor_pdata = {
+ .width = 2,
+ .parts = hydrogen_nor_partitions,
+ .nr_parts = ARRAY_SIZE(hydrogen_nor_partitions),
+};
+
+static struct resource hydrogen_nor_res = {
+ .start = CNS3XXX_FLASH_BASE,
+ .end = CNS3XXX_FLASH_BASE + SZ_32M - 1,
+ .flags = IORESOURCE_MEM | IORESOURCE_MEM_32BIT,
+};
+
+static struct platform_device hydrogen_nor_pdev = {
+ .name = "physmap-flash",
+ .id = 0,
+ .resource = &hydrogen_nor_res,
+ .num_resources = 1,
+ .dev = {
+ .platform_data = &hydrogen_nor_pdata,
+ },
+};
+
+/*
+ * SPI
+ */
+static struct mtd_partition hydrogen_spi_partitions[] = {
+ {
+ .name = "uboot",
+ .size = SZ_512K,
+ .offset = 0,
+ }, {
+ .name = "uboot_env",
+ .size = SZ_128K,
+ .offset = MTDPART_OFS_APPEND,
+ }, {
+ .name = "kernel",
+ .size = SZ_2M,
+ .offset = MTDPART_OFS_APPEND,
+ }, {
+ .name = "rootfs",
+ .size = MTDPART_SIZ_FULL,
+ .offset = MTDPART_OFS_APPEND,
+ },
+};
+
+static struct flash_platform_data hydrogen_spi_pdata = {
+ .parts = hydrogen_spi_partitions,
+ .nr_parts = ARRAY_SIZE(hydrogen_spi_partitions),
+};
+
+static struct spi_board_info hydrogen_spi_devices[] __initdata = {
+ {
+ .modalias = "mx25l12805d",
+ .platform_data = &hydrogen_spi_pdata,
+ .max_speed_hz = 50000000,
+ .bus_num = 1,
+ .chip_select = 0,
+ },
+};
+
+static struct platform_device hydrogen_spi_controller = {
+ .name = "cns3xxx_spi",
+};
+
+/*
+ * Hydrogen has 6 GPIO LEDs, the rest are controlled by the broadcom switch
+ */
+static struct gpio_led hydrogen_gpio_leds[] __initdata = {
+ { .name = "hydrogen:red:status", .gpio = 10, .active_low = 1, },
+ { .name = "hydrogen:green:status", .gpio = 11, .active_low = 1, },
+ { .name = "hydrogen:green:wlan", .gpio = 13, .active_low = 1, },
+ { .name = "hydrogen:red:wlan", .gpio = 14, .active_low = 1, },
+ { .name = "hydrogen:green:voip", .gpio = 16, .active_low = 1, },
+ { .name = "hydrogen:red:voip", .gpio = 17, .active_low = 1, }
+};
+
+static struct gpio_led_platform_data hydrogen_gpio_leds_data = {
+ .num_leds = ARRAY_SIZE(hydrogen_gpio_leds),
+ .leds = hydrogen_gpio_leds,
+};
+
+static struct platform_device hydrogen_gpio_leds_device = {
+ .name = "leds-gpio",
+ .id = -1,
+ .dev.platform_data = &hydrogen_gpio_leds_data,
+};
+
+/*
+ * Ethernet
+ */
+static struct cns3xxx_plat_info hydrogen_net_data = {
+ .ports = 0b011,
+ .phy = { 0, 4, 25 },
+ .hwaddr = {
+ { 0x00, 0x21, 0x94, 0x00, 0x00, 0x00 },
+ { 0x00, 0x21, 0x94, 0x00, 0x00, 0x01 },
+ { 0x00, 0x21, 0x94, 0x00, 0x00, 0x02 },
+ },
+};
+
+static struct platform_device hydrogen_net_device = {
+ .name = "cns3xxx_eth",
+ .id = 0,
+ .dev.platform_data = &hydrogen_net_data,
+};
+
+/*
+ * Hydrogen board has 3 MAC addresses which are passed via kernel command line
+ */
+static int __init
+setup_ethaddr(char *mac)
+{
+ if (!is_valid_ether_addr(mac))
+ return 1;
+
+ if (!mac_pton(mac, hydrogen_net_data.hwaddr[0]))
+ memset(hydrogen_net_data.hwaddr[0], 0, 6);
+
+ return 1;
+}
+__setup("ethaddr=", setup_ethaddr);
+
+static int __init
+setup_eth1addr(char *mac)
+{
+ if (!is_valid_ether_addr(mac))
+ return 1;
+
+ if (!mac_pton(mac, hydrogen_net_data.hwaddr[1]))
+ memset(hydrogen_net_data.hwaddr[1], 0, 6);
+
+ return 1;
+}
+__setup("eth1addr=", setup_eth1addr);
+
+static int __init
+setup_eth2addr(char *mac)
+{
+ if (!is_valid_ether_addr(mac))
+ return 1;
+
+ if (!mac_pton(mac, hydrogen_net_data.hwaddr[2]))
+ memset(hydrogen_net_data.hwaddr[2], 0, 6);
+
+ return 1;
+}
+__setup("eth2addr=", setup_eth2addr);
+
+/*
+ * UART
+ */
+static void __init hydrogen_early_serial_setup(void)
+{
+#ifdef CONFIG_SERIAL_8250_CONSOLE
+ static struct uart_port hydrogen_serial_port = {
+ .membase = (void __iomem *)CNS3XXX_UART0_BASE_VIRT,
+ .mapbase = CNS3XXX_UART0_BASE,
+ .irq = IRQ_CNS3XXX_UART0,
+ .iotype = UPIO_MEM,
+ .flags = UPF_BOOT_AUTOCONF | UPF_FIXED_TYPE,
+ .regshift = 2,
+ .uartclk = 24000000,
+ .line = 0,
+ .type = PORT_16550A,
+ .fifosize = 16,
+ };
+
+ early_serial_setup(&hydrogen_serial_port);
+#endif
+}
+
+/*
+ * USB
+ */
+static struct resource cns3xxx_usb_ehci_resources[] = {
+ [0] = {
+ .start = CNS3XXX_USB_BASE,
+ .end = CNS3XXX_USB_BASE + SZ_16M - 1,
+ .flags = IORESOURCE_MEM,
+ },
+ [1] = {
+ .start = IRQ_CNS3XXX_USB_EHCI,
+ .flags = IORESOURCE_IRQ,
+ },
+};
+
+static u64 cns3xxx_usb_ehci_dma_mask = DMA_BIT_MASK(32);
+
+static struct platform_device cns3xxx_usb_ehci_device = {
+ .name = "cns3xxx-ehci",
+ .num_resources = ARRAY_SIZE(cns3xxx_usb_ehci_resources),
+ .resource = cns3xxx_usb_ehci_resources,
+ .dev = {
+ .dma_mask = &cns3xxx_usb_ehci_dma_mask,
+ .coherent_dma_mask = DMA_BIT_MASK(32),
+ },
+};
+
+static struct resource cns3xxx_usb_ohci_resources[] = {
+ [0] = {
+ .start = CNS3XXX_USB_OHCI_BASE,
+ .end = CNS3XXX_USB_OHCI_BASE + SZ_16M - 1,
+ .flags = IORESOURCE_MEM,
+ },
+ [1] = {
+ .start = IRQ_CNS3XXX_USB_OHCI,
+ .flags = IORESOURCE_IRQ,
+ },
+};
+
+static u64 cns3xxx_usb_ohci_dma_mask = DMA_BIT_MASK(32);
+
+static struct platform_device cns3xxx_usb_ohci_device = {
+ .name = "cns3xxx-ohci",
+ .num_resources = ARRAY_SIZE(cns3xxx_usb_ohci_resources),
+ .resource = cns3xxx_usb_ohci_resources,
+ .dev = {
+ .dma_mask = &cns3xxx_usb_ohci_dma_mask,
+ .coherent_dma_mask = DMA_BIT_MASK(32),
+ },
+};
+
+/*
+ * Initialization
+ */
+static struct platform_device *hydrogen_pdevs[] __initdata = {
+ &hydrogen_nor_pdev,
+ &cns3xxx_usb_ehci_device,
+ &cns3xxx_usb_ohci_device,
+};
+
+static void __init hydrogen_init(void)
+{
+ cns3xxx_l2x0_init();
+ platform_device_register(&hydrogen_gpio_leds_device);
+
+ platform_device_register(&hydrogen_net_device);
+
+ platform_add_devices(ARRAY_AND_SIZE(hydrogen_pdevs));
+
+ if (spi_enable) {
+ platform_device_register(&hydrogen_spi_controller);
+ spi_register_board_info(ARRAY_AND_SIZE(hydrogen_spi_devices));
+ }
+
+ cns3xxx_ahci_init();
+ pm_power_off = cns3xxx_power_off;
+}
+
+static struct map_desc hydrogen_io_desc[] __initdata = {
+ {
+ .virtual = CNS3XXX_UART0_BASE_VIRT,
+ .pfn = __phys_to_pfn(CNS3XXX_UART0_BASE),
+ .length = SZ_4K,
+ .type = MT_DEVICE,
+ },
+};
+
+static void __init hydrogen_map_io(void)
+{
+ cns3xxx_common_init();
+ iotable_init(ARRAY_AND_SIZE(hydrogen_io_desc));
+ hydrogen_early_serial_setup();
+}
+
+
+MACHINE_START(HYDROGEN, "Ping Communication Hydrogen")
+ .atag_offset = 0x100,
+ .map_io = hydrogen_map_io,
+ .init_irq = cns3xxx_init_irq,
+ .timer = &cns3xxx_timer,
+ .handle_irq = gic_handle_irq,
+ .init_machine = hydrogen_init,
+ .restart = cns3xxx_restart,
+MACHINE_END