Resguardo inicial

This commit is contained in:
lastdragon
2026-09-06 12:53:21 -06:00
parent 662efe3c2a
commit ad2088d178
94853 changed files with 43200404 additions and 0 deletions
@@ -0,0 +1,5 @@
# SPDX-License-Identifier: GPL-2.0-only
obj-$(CONFIG_GEODE_COMMON) += geode-common.o
obj-$(CONFIG_ALIX) += alix.o
obj-$(CONFIG_NET5501) += net5501.o
obj-$(CONFIG_GEOS) += geos.o
+136
View File
@@ -0,0 +1,136 @@
// SPDX-License-Identifier: GPL-2.0-only
/*
* System Specific setup for PCEngines ALIX.
* At the moment this means setup of GPIO control of LEDs
* on Alix.2/3/6 boards.
*
* Copyright (C) 2008 Constantin Baranov <const@mimas.ru>
* Copyright (C) 2011 Ed Wildgoose <kernel@wildgooses.com>
* and Philip Prindeville <philipp@redfish-solutions.com>
*
* TODO: There are large similarities with leds-net5501.c
* by Alessandro Zummo <a.zummo@towertech.it>
* In the future leds-net5501.c should be migrated over to platform
*/
#include <linux/kernel.h>
#include <linux/init.h>
#include <linux/io.h>
#include <linux/string.h>
#include <linux/moduleparam.h>
#include <linux/dmi.h>
#include <asm/geode.h>
#include "geode-common.h"
#define BIOS_SIGNATURE_TINYBIOS 0xf0000
#define BIOS_SIGNATURE_COREBOOT 0x500
#define BIOS_REGION_SIZE 0x10000
/*
* This driver is not modular, but to keep back compatibility
* with existing use cases, continuing with module_param is
* the easiest way forward.
*/
static bool force = 0;
module_param(force, bool, 0444);
/* FIXME: Award bios is not automatically detected as Alix platform */
MODULE_PARM_DESC(force, "Force detection as ALIX.2/ALIX.3 platform");
static const struct geode_led alix_leds[] __initconst = {
{ 6, true },
{ 25, false },
{ 27, false },
};
static void __init register_alix(void)
{
geode_create_restart_key(24);
geode_create_leds("alix", alix_leds, ARRAY_SIZE(alix_leds));
}
static bool __init alix_present(unsigned long bios_phys,
const char *alix_sig,
size_t alix_sig_len)
{
const size_t bios_len = BIOS_REGION_SIZE;
const char *bios_virt;
const char *scan_end;
const char *p;
char name[64];
if (force) {
printk(KERN_NOTICE "%s: forced to skip BIOS test, "
"assume system is ALIX.2/ALIX.3\n",
KBUILD_MODNAME);
return true;
}
bios_virt = phys_to_virt(bios_phys);
scan_end = bios_virt + bios_len - (alix_sig_len + 2);
for (p = bios_virt; p < scan_end; p++) {
const char *tail;
char *a;
if (memcmp(p, alix_sig, alix_sig_len) != 0)
continue;
memcpy(name, p, sizeof(name));
/* remove the first \0 character from string */
a = strchr(name, '\0');
if (a)
*a = ' ';
/* cut the string at a newline */
a = strchr(name, '\r');
if (a)
*a = '\0';
tail = p + alix_sig_len;
if ((tail[0] == '2' || tail[0] == '3' || tail[0] == '6')) {
printk(KERN_INFO
"%s: system is recognized as \"%s\"\n",
KBUILD_MODNAME, name);
return true;
}
}
return false;
}
static bool __init alix_present_dmi(void)
{
const char *vendor, *product;
vendor = dmi_get_system_info(DMI_SYS_VENDOR);
if (!vendor || strcmp(vendor, "PC Engines"))
return false;
product = dmi_get_system_info(DMI_PRODUCT_NAME);
if (!product || (strcmp(product, "ALIX.2D") && strcmp(product, "ALIX.6")))
return false;
printk(KERN_INFO "%s: system is recognized as \"%s %s\"\n",
KBUILD_MODNAME, vendor, product);
return true;
}
static int __init alix_init(void)
{
const char tinybios_sig[] = "PC Engines ALIX.";
const char coreboot_sig[] = "PC Engines\0ALIX.";
if (!is_geode())
return 0;
if (alix_present(BIOS_SIGNATURE_TINYBIOS, tinybios_sig, sizeof(tinybios_sig) - 1) ||
alix_present(BIOS_SIGNATURE_COREBOOT, coreboot_sig, sizeof(coreboot_sig) - 1) ||
alix_present_dmi())
register_alix();
return 0;
}
device_initcall(alix_init);
@@ -0,0 +1,188 @@
// SPDX-License-Identifier: GPL-2.0-only
/*
* Shared helpers to register GPIO-connected buttons and LEDs
* on AMD Geode boards.
*/
#include <linux/err.h>
#include <linux/gpio/machine.h>
#include <linux/gpio/property.h>
#include <linux/input.h>
#include <linux/leds.h>
#include <linux/mfd/cs5535.h>
#include <linux/platform_device.h>
#include <linux/slab.h>
#include "geode-common.h"
static const struct property_entry geode_gpio_keys_props[] = {
PROPERTY_ENTRY_U32("poll-interval", 20),
{ }
};
static const struct software_node geode_gpio_keys_node = {
.name = "geode-gpio-keys",
.properties = geode_gpio_keys_props,
};
static struct software_node_ref_args geode_restart_gpio_ref;
static const struct property_entry geode_restart_key_props[] = {
PROPERTY_ENTRY_REF_ARRAY_LEN("gpios", &geode_restart_gpio_ref, 1),
PROPERTY_ENTRY_U32("linux,code", KEY_RESTART),
PROPERTY_ENTRY_STRING("label", "Reset button"),
PROPERTY_ENTRY_U32("debounce-interval", 100),
{ }
};
static const struct software_node geode_restart_key_node = {
.parent = &geode_gpio_keys_node,
.properties = geode_restart_key_props,
};
static const struct software_node *geode_gpio_keys_swnodes[] __initconst = {
&geode_gpio_keys_node,
&geode_restart_key_node,
NULL
};
/*
* Creates gpio-keys-polled device for the restart key.
*
* Note that it needs to be called first, before geode_create_leds(),
* because it registers gpiochip software node used by both gpio-keys and
* leds-gpio devices.
*/
int __init geode_create_restart_key(unsigned int pin)
{
struct platform_device_info keys_info = {
.name = "gpio-keys-polled",
.id = 1,
};
struct platform_device *pd;
int err;
geode_restart_gpio_ref = SOFTWARE_NODE_REFERENCE(&cs5535_gpio_swnode,
pin, GPIO_ACTIVE_LOW);
err = software_node_register_node_group(geode_gpio_keys_swnodes);
if (err) {
pr_err("failed to register gpio-keys software nodes: %d\n", err);
return err;
}
keys_info.fwnode = software_node_fwnode(&geode_gpio_keys_node);
pd = platform_device_register_full(&keys_info);
err = PTR_ERR_OR_ZERO(pd);
if (err) {
pr_err("failed to create gpio-keys device: %d\n", err);
software_node_unregister_node_group(geode_gpio_keys_swnodes);
return err;
}
return 0;
}
static const struct software_node geode_gpio_leds_node = {
.name = "geode-leds",
};
#define MAX_LEDS 3
int __init geode_create_leds(const char *label, const struct geode_led *leds,
unsigned int n_leds)
{
const struct software_node *group[MAX_LEDS + 2] = { 0 };
struct software_node *swnodes;
struct property_entry *props;
struct software_node_ref_args *gpio_refs;
struct platform_device_info led_info = {
.name = "leds-gpio",
.id = PLATFORM_DEVID_NONE,
};
struct platform_device *led_dev;
const char *node_name;
int err;
int i;
if (n_leds > MAX_LEDS) {
pr_err("%s: too many LEDs\n", __func__);
return -EINVAL;
}
swnodes = kzalloc_objs(*swnodes, n_leds);
if (!swnodes)
return -ENOMEM;
/*
* Each LED is represented by 3 properties: "gpios",
* "linux,default-trigger", and am empty terminator.
*/
props = kzalloc_objs(*props, n_leds * 3);
if (!props) {
err = -ENOMEM;
goto err_free_swnodes;
}
gpio_refs = kzalloc_objs(*gpio_refs, n_leds);
if (!gpio_refs) {
err = -ENOMEM;
goto err_free_props;
}
group[0] = &geode_gpio_leds_node;
for (i = 0; i < n_leds; i++) {
node_name = kasprintf(GFP_KERNEL, "%s:%d", label, i);
if (!node_name) {
err = -ENOMEM;
goto err_free_names;
}
gpio_refs[i] = SOFTWARE_NODE_REFERENCE(&cs5535_gpio_swnode,
leds[i].pin,
GPIO_ACTIVE_LOW);
props[i * 3 + 0] =
PROPERTY_ENTRY_REF_ARRAY_LEN("gpios", &gpio_refs[i], 1);
props[i * 3 + 1] =
PROPERTY_ENTRY_STRING("linux,default-trigger",
leds[i].default_on ?
"default-on" : "default-off");
/* props[i * 3 + 2] is an empty terminator */
swnodes[i] = SOFTWARE_NODE(node_name, &props[i * 3],
&geode_gpio_leds_node);
group[i + 1] = &swnodes[i];
}
err = software_node_register_node_group(group);
if (err) {
pr_err("failed to register LED software nodes: %d\n", err);
goto err_free_names;
}
led_info.fwnode = software_node_fwnode(&geode_gpio_leds_node);
led_dev = platform_device_register_full(&led_info);
err = PTR_ERR_OR_ZERO(led_dev);
if (err) {
pr_err("failed to create LED device: %d\n", err);
goto err_unregister_group;
}
return 0;
err_unregister_group:
software_node_unregister_node_group(group);
err_free_names:
while (--i >= 0)
kfree(swnodes[i].name);
kfree(gpio_refs);
err_free_props:
kfree(props);
err_free_swnodes:
kfree(swnodes);
return err;
}
MODULE_IMPORT_NS("CS5535");
@@ -0,0 +1,21 @@
// SPDX-License-Identifier: GPL-2.0-only
/*
* Shared helpers to register GPIO-connected buttons and LEDs
* on AMD Geode boards.
*/
#ifndef __PLATFORM_GEODE_COMMON_H
#define __PLATFORM_GEODE_COMMON_H
#include <linux/property.h>
struct geode_led {
unsigned int pin;
bool default_on;
};
int geode_create_restart_key(unsigned int pin);
int geode_create_leds(const char *label, const struct geode_led *leds,
unsigned int n_leds);
#endif /* __PLATFORM_GEODE_COMMON_H */
@@ -0,0 +1,59 @@
// SPDX-License-Identifier: GPL-2.0-only
/*
* System Specific setup for Traverse Technologies GEOS.
* At the moment this means setup of GPIO control of LEDs.
*
* Copyright (C) 2008 Constantin Baranov <const@mimas.ru>
* Copyright (C) 2011 Ed Wildgoose <kernel@wildgooses.com>
* and Philip Prindeville <philipp@redfish-solutions.com>
*
* TODO: There are large similarities with leds-net5501.c
* by Alessandro Zummo <a.zummo@towertech.it>
* In the future leds-net5501.c should be migrated over to platform
*/
#include <linux/kernel.h>
#include <linux/init.h>
#include <linux/io.h>
#include <linux/string.h>
#include <linux/dmi.h>
#include <asm/geode.h>
#include "geode-common.h"
static const struct geode_led geos_leds[] __initconst = {
{ 6, true },
{ 25, false },
{ 27, false },
};
static void __init register_geos(void)
{
geode_create_restart_key(3);
geode_create_leds("geos", geos_leds, ARRAY_SIZE(geos_leds));
}
static int __init geos_init(void)
{
const char *vendor, *product;
if (!is_geode())
return 0;
vendor = dmi_get_system_info(DMI_SYS_VENDOR);
if (!vendor || strcmp(vendor, "Traverse Technologies"))
return 0;
product = dmi_get_system_info(DMI_PRODUCT_NAME);
if (!product || strcmp(product, "Geos"))
return 0;
printk(KERN_INFO "%s: system is recognized as \"%s %s\"\n",
KBUILD_MODNAME, vendor, product);
register_geos();
return 0;
}
device_initcall(geos_init);
@@ -0,0 +1,97 @@
// SPDX-License-Identifier: GPL-2.0-only
/*
* System Specific setup for Soekris net5501
* At the moment this means setup of GPIO control of LEDs and buttons
* on net5501 boards.
*
* Copyright (C) 2008-2009 Tower Technologies
* Written by Alessandro Zummo <a.zummo@towertech.it>
*
* Copyright (C) 2008 Constantin Baranov <const@mimas.ru>
* Copyright (C) 2011 Ed Wildgoose <kernel@wildgooses.com>
* and Philip Prindeville <philipp@redfish-solutions.com>
*/
#include <linux/kernel.h>
#include <linux/init.h>
#include <linux/io.h>
#include <linux/string.h>
#include <linux/input.h>
#include <linux/gpio/machine.h>
#include <linux/gpio/property.h>
#include <asm/geode.h>
#include "geode-common.h"
#define BIOS_REGION_BASE 0xffff0000
#define BIOS_REGION_SIZE 0x00010000
static const struct geode_led net5501_leds[] __initconst = {
{ 6, true },
};
static void __init register_net5501(void)
{
geode_create_restart_key(24);
geode_create_leds("net5501", net5501_leds, ARRAY_SIZE(net5501_leds));
}
struct net5501_board {
u16 offset;
u16 len;
char *sig;
};
static struct net5501_board __initdata boards[] = {
{ 0xb7b, 7, "net5501" }, /* net5501 v1.33/1.33c */
{ 0xb1f, 7, "net5501" }, /* net5501 v1.32i */
};
static bool __init net5501_present(void)
{
int i;
unsigned char *rombase, *bios;
bool found = false;
rombase = ioremap(BIOS_REGION_BASE, BIOS_REGION_SIZE - 1);
if (!rombase) {
printk(KERN_ERR "%s: failed to get rombase\n", KBUILD_MODNAME);
return found;
}
bios = rombase + 0x20; /* null terminated */
if (memcmp(bios, "comBIOS", 7))
goto unmap;
for (i = 0; i < ARRAY_SIZE(boards); i++) {
unsigned char *model = rombase + boards[i].offset;
if (!memcmp(model, boards[i].sig, boards[i].len)) {
printk(KERN_INFO "%s: system is recognized as \"%s\"\n",
KBUILD_MODNAME, model);
found = true;
break;
}
}
unmap:
iounmap(rombase);
return found;
}
static int __init net5501_init(void)
{
if (!is_geode())
return 0;
if (!net5501_present())
return 0;
register_net5501();
return 0;
}
device_initcall(net5501_init);