<html><head></head><body><div style="font-family: Verdana;font-size: 12.0px;"><div>
<div>Hi!</div>

<div> </div>

<div>We just got a bunch of PC Engines APU boards and tried them with Voyage and plain vanilla Jessie.</div>

<div> </div>

<div>First, the boards are pretty good.  They are for sure not the fastest ones on the market but they are much more faster than Alix boards - so, as intelligent routers or automation servers they are really good.  And they seem to run stable!</div>

<div> </div>

<div>Things that changed are the ports for LEDs.  On Alix boards we used LEDs pretty heavily as they are the only way for such a headless box to communicate with the humans around.</div>

<div> </div>

<div>I took the old Alix driver, used a bit of google and came up with the APU driver that I attached (well after that I found out that someone else already did that, too ;-).</div>

<div> </div>

<div>This driver works fine for sorts of ledtriggers such as heartbeat, timer, etc.</div>

<div> </div>

<div>But, it does not work with ledtrig-netdev.  Why?</div>

<div> </div>

<div>When I write "netdev" to triggers file then I get back a "character combination" that logs me off. -Strange-  When I now do a cat triggers then the session seems to stop.  The APU seems to be in a very unstable condition after that.  The kernel did GP 2 times and rebooted.  Sometimes even the watchdog does not reboot the APU.  I have no clue what happened to netdev trigger.  I believe that the APU LED driver is ok (it's no magic).</div>

<div> </div>

<div>I also tried that with plain Jessie.  Jessie does not come with the APU LED or the netdev drivers, so I incorporated them myself.  Same behaviour as with Voyage.  So, is it possible that there is a concrete reason why Jessie does not include the netdev driver?  May the reason be that it is simply broken and/or does not work with newer kernels/net devices anymore?  Does anyone know?</div>

<div> </div>

<div>To make that story short.  Can someone with APU boards please check if they see same behaviour?  And can someone please review the APU LEDs driver (maybe I am missing something).  Does anybody have an idea how to fix that netdev problem with APU or is someone interested in helping with it?  (Currently I have my dev env on Jessie on APU and will try with voyage after it works with the "reference").</div>

<div> </div>

<div>Thanks a lot!<br/>
-lutzn</div>

<div> </div>

<div> </div>

<div> </div>

<div>/*<br/>
 * LEDs driver for PCEngines APU series<br/>
 *<br/>
 * Copyright (C) 2014 me (based on 2007 Petr Leibman)<br/>
 *<br/>
 * Based on leds-wrap.c<br/>
 *<br/>
 * This program is free software; you can redistribute it and/or modify<br/>
 * it under the terms of the GNU General Public License version 2 as<br/>
 * published by the Free Software Foundation.<br/>
 */</div>

<div>#include <linux/kernel.h><br/>
#include <linux/module.h><br/>
#include <linux/init.h><br/>
#include <linux/platform_device.h><br/>
#include <linux/leds.h><br/>
#include <linux/err.h><br/>
#include <asm/io.h></div>

<div>#define DRVNAME "apu-led"</div>

<div>#define BASEADDR                (0xFED801BD)<br/>
#define LEDON                   (0x8)<br/>
#define LEDOFF                  (0xC8)</div>

<div>static struct platform_device *pdev;<br/>
unsigned int *p1, *p2, *p3;</div>

<div>static void apu_led_set_1(struct led_classdev *led_cdev,<br/>
                enum led_brightness value)<br/>
{<br/>
        if (value)<br/>
                iowrite8(LEDON, p1);<br/>
        else<br/>
                iowrite8(LEDOFF, p1);<br/>
}</div>

<div>static void apu_led_set_2(struct led_classdev *led_cdev,<br/>
                enum led_brightness value)<br/>
{<br/>
        if (value)<br/>
                iowrite8(LEDON, p2);<br/>
        else<br/>
                iowrite8(LEDOFF, p2);<br/>
}</div>

<div>static void apu_led_set_3(struct led_classdev *led_cdev,<br/>
                enum led_brightness value)<br/>
{<br/>
        if (value)<br/>
                iowrite8(LEDON, p3);<br/>
        else<br/>
                iowrite8(LEDOFF, p3);<br/>
}</div>

<div>static struct led_classdev apu_led_1 = {<br/>
        .name           = "apu:1",<br/>
        .brightness_set = apu_led_set_1,<br/>
};</div>

<div>static struct led_classdev apu_led_2 = {<br/>
        .name           = "apu:2",<br/>
        .brightness_set = apu_led_set_2,<br/>
};</div>

<div>static struct led_classdev apu_led_3 = {<br/>
        .name           = "apu:3",<br/>
        .brightness_set = apu_led_set_3,<br/>
};</div>

<div><br/>
#ifdef CONFIG_PM<br/>
static int apu_led_suspend(struct platform_device *dev,<br/>
                pm_message_t state)<br/>
{<br/>
        led_classdev_suspend(&apu_led_1);<br/>
        led_classdev_suspend(&apu_led_2);<br/>
        led_classdev_suspend(&apu_led_3);<br/>
        return 0;<br/>
}</div>

<div>static int apu_led_resume(struct platform_device *dev)<br/>
{<br/>
        led_classdev_resume(&apu_led_1);<br/>
        led_classdev_resume(&apu_led_2);<br/>
        led_classdev_resume(&apu_led_3);<br/>
        return 0;<br/>
}<br/>
#else<br/>
#define apu_led_suspend NULL<br/>
#define apu_led_resume NULL<br/>
#endif</div>

<div>static int apu_led_probe(struct platform_device *pdev)<br/>
{<br/>
        int ret;</div>

<div>        ret = led_classdev_register(&pdev->dev, &apu_led_1);<br/>
        if (ret == 0)<br/>
        {<br/>
                ret = led_classdev_register(&pdev->dev, &apu_led_2);<br/>
                if (ret >= 0)<br/>
                {<br/>
                        ret = led_classdev_register(&pdev->dev, &apu_led_3);<br/>
                        if (ret < 0)<br/>
                                led_classdev_unregister(&apu_led_2);<br/>
                }<br/>
                if (ret < 0)<br/>
                        led_classdev_unregister(&apu_led_1);<br/>
        }<br/>
        return ret;<br/>
}</div>

<div>static int apu_led_remove(struct platform_device *pdev)<br/>
{<br/>
        led_classdev_unregister(&apu_led_1);<br/>
        led_classdev_unregister(&apu_led_2);<br/>
        led_classdev_unregister(&apu_led_3);<br/>
        return 0;<br/>
}</div>

<div>static struct platform_driver apu_led_driver = {<br/>
        .probe          = apu_led_probe,<br/>
        .remove         = apu_led_remove,<br/>
        .suspend        = apu_led_suspend,<br/>
        .resume         = apu_led_resume,<br/>
        .driver         = {<br/>
        .name           = DRVNAME,<br/>
        .owner          = THIS_MODULE,<br/>
        },<br/>
};</div>

<div>static int __init apu_led_init(void)<br/>
{<br/>
        int ret;</div>

<div>        ret = platform_driver_register(&apu_led_driver);<br/>
        if (ret < 0)<br/>
                goto out;</div>

<div>        pdev = platform_device_register_simple(DRVNAME, -1, NULL, 0);<br/>
        if (IS_ERR(pdev)) {<br/>
                ret = PTR_ERR(pdev);<br/>
                platform_driver_unregister(&apu_led_driver);<br/>
                goto out;<br/>
        }</div>

<div>        p1 = ioremap(BASEADDR, 1);<br/>
        p2 = ioremap(BASEADDR+1, 1);<br/>
        p3 = ioremap(BASEADDR+2, 1);</div>

<div>out:<br/>
        return ret;<br/>
}</div>

<div>static void __exit apu_led_exit(void)<br/>
{<br/>
        platform_device_unregister(pdev);<br/>
        platform_driver_unregister(&apu_led_driver);<br/>
}</div>

<div>module_init(apu_led_init);<br/>
module_exit(apu_led_exit);</div>

<div>MODULE_AUTHOR("me");<br/>
MODULE_DESCRIPTION("PCEngines APU LED driver");<br/>
MODULE_LICENSE("GPL");</div>

<div> </div>
</div></div></body></html>