Merge pull request #18 from opencomputeproject/master

sync with ocp
This commit is contained in:
DeltaProducts
2017-12-29 09:01:03 +08:00
committed by GitHub
164 changed files with 12078 additions and 38 deletions

View File

@@ -144,7 +144,14 @@ if test "$installer_debug"; then
fi
# Pickup ONIE defines for this machine.
if test -r /etc/machine.conf; then
if test "$onie_platform"; then
:
else
onie_platform=$(onie-sysinfo -p 2>/dev/null) || :
fi
if test "$onie_platform"; then
:
elif test -r /etc/machine.conf; then
. /etc/machine.conf
fi
@@ -252,7 +259,7 @@ if test "${onie_platform}"; then
}
else
if test "$ARCH_X86"; then
echo "Missing onie_platform (invalid /etc/machine.conf)" 1>&2
echo "Missing onie_platform (invalid or missing onie-sysinfo or /etc/machine.conf)" 1>&2
exit 1
fi
#

View File

@@ -0,0 +1,7 @@
#!/usr/bin/python
"""Run native onie-sysinfo
"""
import onl.install.ShellApp
onl.install.ShellApp.OnieSysinfoApp.main()

View File

@@ -122,7 +122,7 @@ installer_mkchroot() {
mkdir -p "${rootdir}${TMPDIR}"
fi
# export ONIE defines to the installer
# export ONIE defines to the installer, if they exist
if test -r /etc/machine.conf; then
cp /etc/machine.conf "${rootdir}/etc/machine.conf"
fi

View File

@@ -17,7 +17,7 @@ import time
from InstallUtils import InitrdContext
from InstallUtils import SubprocessMixin
from InstallUtils import ProcMountsParser
from ShellApp import OnieBootContext
from ShellApp import OnieBootContext, OnieSysinfo
import ConfUtils, BaseInstall
class App(SubprocessMixin, object):
@@ -129,7 +129,7 @@ class App(SubprocessMixin, object):
def runLocalOrChroot(self):
if self.machineConf is None:
self.log.error("missing machine.conf")
self.log.error("missing onie-sysinfo or machine.conf")
return 1
if self.installerConf is None:
self.log.error("missing installer.conf")
@@ -230,10 +230,17 @@ class App(SubprocessMixin, object):
def runLocal(self):
self.log.info("getting installer configuration")
if os.path.exists(ConfUtils.MachineConf.PATH):
osi = OnieSysinfo(log=self.log.getChild("onie-sysinfo"))
try:
halp = osi.help
except AttributeError:
halp = None
if halp is not None:
self.machineConf = osi
elif os.path.exists(ConfUtils.MachineConf.PATH):
self.machineConf = ConfUtils.MachineConf()
else:
self.log.warn("missing /etc/machine.conf from ONIE runtime")
self.log.warn("missing onie-sysinfo or /etc/machine.conf from ONIE runtime")
self.machineConf = ConfUtils.MachineConf(path='/dev/null')
self.installerConf = ConfUtils.InstallerConf()
@@ -243,7 +250,7 @@ class App(SubprocessMixin, object):
def findPlatform(self):
plat = arch = None
if os.path.exists(ConfUtils.MachineConf.PATH):
if self.machineConf is not None:
plat = getattr(self.machineConf, 'onie_platform', None)
arch = getattr(self.machineConf, 'onie_arch', None)
if plat and arch:

View File

@@ -15,9 +15,6 @@ from InstallUtils import ProcMountsParser, ProcMtdParser
from InstallUtils import BlkidParser
from InstallUtils import UbootInitrdContext
import onl.platform.current
from onl.sysconfig import sysconfig
class AppBase(SubprocessMixin, object):
@property
@@ -228,6 +225,105 @@ class Onie(AppBase):
with OnieBootContext(log=self.log) as ctx:
return self._runInitrdShell(ctx.initrd)
class OnieSysinfoApp(SubprocessMixin, object):
PROG = "onie-sysinfo"
def __init__(self, args=[], log=None):
if log is not None:
self.log = log
else:
self.log = logging.getLogger(self.__class__.__name__)
self.args = args or ['-p',]
self.output = None
def _runInitrdShell(self, initrd):
with InitrdContext(initrd=initrd, log=self.log) as ctx:
cmd = ['onie-sysinfo',]
cmd.extend(self.args)
cmd = ('chroot', ctx.dir,
'/bin/sh', '-c', 'IFS=;' + " ".join(cmd))
try:
self.output = self.check_output(cmd)
ret = 0
except subprocess.CalledProcessError, what:
self.log.error("failed command: %s", " ".join(what.cmd))
for line in (what.output or "").splitlines():
self.log.error(">>> %s", line)
ret = what.returncode
return ret
def run(self):
with OnieBootContext(log=self.log) as ctx:
ret = self._runInitrdShell(ctx.initrd)
if self.output is not None:
sys.stdout.write(self.output)
return ret
def shutdown(self):
pass
@classmethod
def main(cls):
logging.basicConfig()
logger = logging.getLogger(cls.PROG)
logger.setLevel(logging.INFO)
args = list(sys.argv[1:])
sysinfoArgs = []
while args:
if args[0] in ('-v', '--verbose',):
logger.setLevel(logging.DEBUG)
args.pop(0)
continue
if args[0] in ('-q', '--quiet',):
logger.setLevel(logging.ERROR)
args.pop(0)
continue
sysinfoArgs.append(args.pop(0))
app = cls(args=sysinfoArgs, log=logger)
try:
code = app.run()
except:
logger.exception("runner failed")
code = 1
app.shutdown()
sys.exit(code)
class OnieSysinfo(OnieSysinfoApp):
def _runArgs(self, *args):
self.args = args
with OnieBootContext(log=self.log) as ctx:
ret = self._runInitrdShell(ctx.initrd)
if self.output is not None:
return self.output.rstrip()
raise AttributeError("cannot retrieve onie-sysinfo attribute via %s" % str(args))
@property
def help(self):
return self._runArgs('-h')
@property
def onie_platform(self):
return self._runArgs('-p')
@property
def onie_arch(self):
return self._runArgs('-c')
@property
def onie_version(self):
return self._runArgs('-v')
# XXX roth other switches too
class Loader(AppBase):
"""Application shell that uses the (installed) loader runtime."""
@@ -331,6 +427,7 @@ class Loader(AppBase):
def run(self):
import onl.platform.current
self.platform = onl.platform.current.OnlPlatform()
self.pc = self.platform.platform_config
@@ -353,6 +450,7 @@ class Upgrader(AppBase):
def runGrub(self):
from onl.sysconfig import sysconfig
d = sysconfig.upgrade.loader.package.dir
for b in sysconfig.upgrade.loader.package.grub:
p = os.path.join(d, b)
@@ -365,6 +463,7 @@ class Upgrader(AppBase):
def runUboot(self):
from onl.sysconfig import sysconfig
d = sysconfig.upgrade.loader.package.dir
for b in sysconfig.upgrade.loader.package.fit:
p = os.path.join(d, b)
@@ -377,6 +476,7 @@ class Upgrader(AppBase):
def run(self):
import onl.platform.current
self.platform = onl.platform.current.OnlPlatform()
self.pc = self.platform.platform_config

View File

@@ -60,8 +60,9 @@ class App(SubprocessMixin):
src = os.path.join(octx.initrdDir, "etc/machine.conf")
dst = os.path.join(ctx.dir, "etc/machine.conf")
self.log.debug("+ /bin/cp %s %s", src, dst)
shutil.copy2(src, dst)
if os.path.exists(src):
self.log.debug("+ /bin/cp %s %s", src, dst)
shutil.copy2(src, dst)
src = "/etc/fw_env.config"
if os.path.exists(src):

View File

@@ -486,6 +486,10 @@ class OnlPlatformPortConfig_48x10_6x40(object):
PORT_COUNT=54
PORT_CONFIG="48x10 + 6x40"
class OnlPlatformPortConfig_48x10_4x100(object):
PORT_COUNT=52
PORT_CONFIG="48x10 + 4x100"
class OnlPlatformPortConfig_48x25_6x100(object):
PORT_COUNT=54
PORT_CONFIG="48x25 + 6x100"
@@ -506,6 +510,10 @@ class OnlPlatformPortConfig_32x100(object):
PORT_COUNT=32
PORT_CONFIG="32x100"
class OnlPlatformPortConfig_64x100(object):
PORT_COUNT=64
PORT_CONFIG="64x100"
class OnlPlatformPortConfig_24x1_4x10(object):
PORT_COUNT=28
PORT_CONFIG="24x1 + 4x10"

View File

@@ -61,6 +61,13 @@ def baseconfig():
ONLPDUMP = "%s/bin/onlpdump" % (platform.basedir_onl())
try:
import dmidecode
with open("%s/dmi-system-version" % platform.basedir_onl(), "w") as f:
f.write(dmidecode.QuerySection('system')['0x0001']['data']['Version'])
except:
pass
if not platform.baseconfig():
msg("*** platform class baseconfig failed.\n", fatal=True)

View File

@@ -14,8 +14,9 @@
# platform-config packages.
#
############################################################
import os
import os, sys
import importlib
import subprocess
def platform_name_get():
# Determine the current platform name.
@@ -23,6 +24,22 @@ def platform_name_get():
if os.path.exists("/etc/onl/platform"):
with open("/etc/onl/platform", 'r') as f:
platform=f.read().strip()
elif os.path.exists("/bin/onie-sysinfo"):
try:
platform = subprocess.check_output(('/bin/onie-sysinfo', '-p',)).strip()
except subprocess.CalledProcessError as what:
for line in (what.output or "").splitlines():
sys.stderr.write(">>> %s\n" % line)
sys.stderr.write("onie-sysinfo failed with code %d\n" % what.returncode)
platform = None
elif os.path.exists("/usr/bin/onie-shell"):
try:
platform = subprocess.check_output(('/usr/bin/onie-shell', '-c', "onie-sysinfo -p",)).strip()
except subprocess.CalledProcessError as what:
for line in (what.output or "").splitlines():
sys.stderr.write(">>> %s\n" % line)
sys.stderr.write("onie-sysinfo (onie-shell) failed with code %d\n" % what.returncode)
platform = None
elif os.path.exists("/etc/machine.conf"):
with open("/etc/machine.conf", 'r') as f:
lines = f.readlines(False)

View File

@@ -12,7 +12,7 @@ from onl.upgrade import ubase
from onl.sysconfig import sysconfig
from onl.mounts import OnlMountManager, OnlMountContextReadOnly, OnlMountContextReadWrite
from onl.install import BaseInstall, ConfUtils, InstallUtils
from onl.install.ShellApp import OnieBootContext
from onl.install.ShellApp import OnieBootContext, OnieSysinfo
import onl.platform.current
import onl.versions
@@ -83,8 +83,12 @@ class LoaderUpgrade_Fit(LoaderUpgradeBase):
onlPlatform = onl.platform.current.OnlPlatform()
with OnieBootContext(log=self.logger) as octx:
path = os.path.join(octx.initrdDir, "etc/machine.conf")
machineConf = ConfUtils.MachineConf(path=path)
if os.path.exists("/usr/bin/onie-shell"):
machineConf = OnieSysinfo(log=self.logger.getChild("onie-sysinfo"))
else:
path = os.path.join(octx.initrdDir, "etc/machine.conf")
if os.path.exists(path):
machineConf = ConfUtils.MachineConf(path=path)
installerConf = ConfUtils.InstallerConf(path="/dev/null")
# start with an empty installerConf, fill it in piece by piece

View File

@@ -2004,7 +2004,7 @@ CONFIG_GPIO_GENERIC_PLATFORM=y
# CONFIG_GPIO_F7188X is not set
# CONFIG_GPIO_SCH311X is not set
CONFIG_GPIO_SCH=y
# CONFIG_GPIO_ICH is not set
CONFIG_GPIO_ICH=m
# CONFIG_GPIO_VX855 is not set
# CONFIG_GPIO_LYNXPOINT is not set

View File

@@ -31,8 +31,11 @@
#include <linux/mutex.h>
#include <linux/sysfs.h>
#include <linux/slab.h>
#include <linux/delay.h>
#define MAX_FAN_DUTY_CYCLE 100
#define MAX_FAN_DUTY_CYCLE 100
#define I2C_RW_RETRY_COUNT 10
#define I2C_RW_RETRY_INTERVAL 60 /* ms */
/* Addresses scanned
*/
@@ -41,6 +44,7 @@ static const unsigned short normal_i2c[] = { I2C_CLIENT_END };
enum chips {
YM2651,
YM2401,
YM2851,
};
/* Each client has this additional data
@@ -67,6 +71,7 @@ struct ym2651y_data {
u8 mfr_id[10]; /* Register value */
u8 mfr_model[16]; /* Register value */
u8 mfr_revsion[3]; /* Register value */
u8 mfr_serial[20]; /* Register value */
u16 mfr_vin_min; /* Register value */
u16 mfr_vin_max; /* Register value */
u16 mfr_iin_max; /* Register value */
@@ -112,6 +117,7 @@ enum ym2651y_sysfs_attributes {
PSU_MFR_ID,
PSU_MFR_MODEL,
PSU_MFR_REVISION,
PSU_MFR_SERIAL,
PSU_MFR_VIN_MIN,
PSU_MFR_VIN_MAX,
PSU_MFR_VOUT_MIN,
@@ -140,6 +146,7 @@ static SENSOR_DEVICE_ATTR(psu_pmbus_revision,S_IRUGO, show_byte, NULL, PSU_PMB
static SENSOR_DEVICE_ATTR(psu_mfr_id, S_IRUGO, show_ascii, NULL, PSU_MFR_ID);
static SENSOR_DEVICE_ATTR(psu_mfr_model, S_IRUGO, show_ascii, NULL, PSU_MFR_MODEL);
static SENSOR_DEVICE_ATTR(psu_mfr_revision, S_IRUGO, show_ascii, NULL, PSU_MFR_REVISION);
static SENSOR_DEVICE_ATTR(psu_mfr_serial, S_IRUGO, show_ascii, NULL, PSU_MFR_SERIAL);
static SENSOR_DEVICE_ATTR(psu_mfr_vin_min, S_IRUGO, show_linear, NULL, PSU_MFR_VIN_MIN);
static SENSOR_DEVICE_ATTR(psu_mfr_vin_max, S_IRUGO, show_linear, NULL, PSU_MFR_VIN_MAX);
static SENSOR_DEVICE_ATTR(psu_mfr_vout_min, S_IRUGO, show_linear, NULL, PSU_MFR_VOUT_MIN);
@@ -166,6 +173,7 @@ static struct attribute *ym2651y_attributes[] = {
&sensor_dev_attr_psu_mfr_id.dev_attr.attr,
&sensor_dev_attr_psu_mfr_model.dev_attr.attr,
&sensor_dev_attr_psu_mfr_revision.dev_attr.attr,
&sensor_dev_attr_psu_mfr_serial.dev_attr.attr,
&sensor_dev_attr_psu_mfr_vin_min.dev_attr.attr,
&sensor_dev_attr_psu_mfr_vin_max.dev_attr.attr,
&sensor_dev_attr_psu_mfr_pout_max.dev_attr.attr,
@@ -370,6 +378,9 @@ static ssize_t show_ascii(struct device *dev, struct device_attribute *da,
case PSU_MFR_REVISION: /* psu_mfr_revision */
ptr = data->mfr_revsion + 1; /* The first byte is the count byte of string. */
break;
case PSU_MFR_SERIAL: /* psu_mfr_serial */
ptr = data->mfr_serial + 1; /* The first byte is the count byte of string. */
break;
default:
return 0;
}
@@ -477,6 +488,7 @@ static int ym2651y_remove(struct i2c_client *client)
static const struct i2c_device_id ym2651y_id[] = {
{ "ym2651", YM2651 },
{ "ym2401", YM2401 },
{ "ym2851", YM2851 },
{}
};
MODULE_DEVICE_TABLE(i2c, ym2651y_id);
@@ -494,35 +506,75 @@ static struct i2c_driver ym2651y_driver = {
static int ym2651y_read_byte(struct i2c_client *client, u8 reg)
{
return i2c_smbus_read_byte_data(client, reg);
int status = 0, retry = I2C_RW_RETRY_COUNT;
while (retry) {
status = i2c_smbus_read_byte_data(client, reg);
if (unlikely(status < 0)) {
msleep(I2C_RW_RETRY_INTERVAL);
retry--;
continue;
}
break;
}
return status;
}
static int ym2651y_read_word(struct i2c_client *client, u8 reg)
{
return i2c_smbus_read_word_data(client, reg);
int status = 0, retry = I2C_RW_RETRY_COUNT;
while (retry) {
status = i2c_smbus_read_word_data(client, reg);
if (unlikely(status < 0)) {
msleep(I2C_RW_RETRY_INTERVAL);
retry--;
continue;
}
break;
}
return status;
}
static int ym2651y_write_word(struct i2c_client *client, u8 reg, u16 value)
{
return i2c_smbus_write_word_data(client, reg, value);
int status = 0, retry = I2C_RW_RETRY_COUNT;
while (retry) {
status = i2c_smbus_write_word_data(client, reg, value);
if (unlikely(status < 0)) {
msleep(I2C_RW_RETRY_INTERVAL);
retry--;
continue;
}
break;
}
return status;
}
static int ym2651y_read_block(struct i2c_client *client, u8 command, u8 *data,
int data_len)
{
int result = i2c_smbus_read_i2c_block_data(client, command, data_len, data);
int status = 0, retry = I2C_RW_RETRY_COUNT;
if (unlikely(result < 0))
goto abort;
if (unlikely(result != data_len)) {
result = -EIO;
goto abort;
while (retry) {
status = i2c_smbus_read_i2c_block_data(client, command, data_len, data);
if (unlikely(status < 0)) {
msleep(I2C_RW_RETRY_INTERVAL);
retry--;
continue;
}
break;
}
result = 0;
abort:
return result;
return status;
}
struct reg_data_byte {
@@ -651,6 +703,17 @@ static struct ym2651y_data *ym2651y_update_device(struct device *dev)
goto exit;
}
/* Read mfr_serial */
command = 0x9e;
status = ym2651y_read_block(client, command, data->mfr_serial,
ARRAY_SIZE(data->mfr_serial)-1);
data->mfr_serial[ARRAY_SIZE(data->mfr_serial)-1] = '\0';
if (status < 0) {
dev_dbg(&client->dev, "reg %d, err %d\n", command, status);
goto exit;
}
data->last_updated = jiffies;
data->valid = 1;
}

View File

@@ -968,7 +968,6 @@ _sff8472_media_sfp28_cr(const uint8_t* idprom)
/* module should be sfp */
if (!SFF8472_MODULE_SFP(idprom)) return 0;
if (idprom[2] != SFF8472_CONN_NOSEP) return 0;
if ((idprom[3] & SFF8472_CC3_INF_1X_CU_PASSIVE) == 0) return 0;
if (idprom[12] == 0xFF) return 1;

View File

@@ -17,6 +17,7 @@ static sff_ns_entry_t nonstandard_modules__[] =
{ "CISCO-OEM ", "QSFP-4SFP+-CU3M ", SFF_MODULE_TYPE_40G_BASE_CR4, 3 },
{ "CISCO-OEM ", "QSFP-4SFP+-CU5M ", SFF_MODULE_TYPE_40G_BASE_CR4, 5 },
{ "Mellanox ", "MC2206130-001 ", SFF_MODULE_TYPE_40G_BASE_CR4, 1 },
{ "OEM ", "F4M-QSSFP-C-2-30", SFF_MODULE_TYPE_40G_BASE_CR4, 2 },
{},
};

View File

@@ -472,6 +472,7 @@ sff_eeprom_parse_standard__(sff_eeprom_t* se, uint8_t* eeprom)
se->info.length = se->eeprom[146];
break;
case SFF_SFP_TYPE_SFP:
case SFF_SFP_TYPE_SFP28:
se->info.length = se->eeprom[18];
break;
default:

View File

@@ -34,6 +34,8 @@
#define SFF_25G_BASE_SR_PROPERTIES \
SFF_SFP_TYPE_SFP28, "SFP28", SFF_MODULE_TYPE_25G_BASE_SR, "25GBASE-SR", SFF_MEDIA_TYPE_FIBER, "Fiber",SFF_MODULE_CAPS_F_25G
#define SFF_25G_BASE_CR_PROPERTIES \
SFF_SFP_TYPE_SFP28, "SFP28", SFF_MODULE_TYPE_25G_BASE_CR, "25GBASE-CR", SFF_MEDIA_TYPE_COPPER, "Copper", SFF_MODULE_CAPS_F_25G
#define SFF_40G_BASE_SR4_PROPERTIES \
SFF_SFP_TYPE_QSFP_PLUS, "QSFP+", SFF_MODULE_TYPE_40G_BASE_SR4, "40GBASE-SR4", SFF_MEDIA_TYPE_FIBER, "Fiber", SFF_MODULE_CAPS_F_40G
@@ -1626,6 +1628,180 @@ static sff_db_entry_t sff_database__[] =
},
},
},
{
{
.eeprom = {
0x0d, 0x00, 0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x43, 0x4d, 0x50, 0x51, 0x41, 0x41, 0x31, 0x43, 0x41, 0x41, 0x33, 0x37, 0x2d, 0x31,
0x33, 0x32, 0x31, 0x2d, 0x30, 0x32, 0x56, 0x30, 0x32, 0x20, 0x51, 0x53, 0x46, 0x50, 0x2d, 0xe6,
0x53, 0x46, 0x50, 0x31, 0x30, 0x47, 0x2d, 0x43, 0x55, 0x32, 0x4d, 0x20, 0x20, 0x20, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x35,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x0d, 0x00, 0x23, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x05, 0x67, 0x00, 0x00, 0x00,
0x00, 0x00, 0x02, 0xa0, 0x4f, 0x45, 0x4d, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20,
0x20, 0x20, 0x20, 0x20, 0x00, 0x78, 0xa7, 0x14, 0x46, 0x34, 0x4d, 0x2d, 0x51, 0x53, 0x53, 0x46,
0x50, 0x2d, 0x43, 0x2d, 0x32, 0x2d, 0x33, 0x30, 0x41, 0x20, 0x09, 0x0d, 0x00, 0x00, 0x46, 0x8f,
0x00, 0x00, 0x00, 0x00, 0x47, 0x45, 0x31, 0x36, 0x30, 0x34, 0x30, 0x39, 0x32, 0x33, 0x33, 0x33,
0x20, 0x20, 0x20, 0x20, 0x31, 0x36, 0x30, 0x34, 0x30, 0x38, 0x20, 0x20, 0x00, 0x00, 0xe2, 0x60,
0x00, 0x00, 0x11, 0x92, 0x93, 0x56, 0x08, 0x23, 0xce, 0x3b, 0x71, 0x35, 0xac, 0x37, 0xdc, 0x38,
0x1d, 0x13, 0xcb, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1d, 0x36, 0xa4, 0x00,
},
.info = {
"OEM ",
"F4M-QSSFP-C-2-30",
"GE1604092333 ",
SFF_40G_BASE_CR4_PROPERTIES,
2,
},
},
},
{
{
.eeprom = {
0x03, 0x04, 0x23, 0x01, 0x00, 0x00, 0x00, 0x00, 0x84, 0x00, 0x00, 0x06, 0xff, 0x00, 0x00, 0x00,
0x00, 0x00, 0x01, 0x00, 0x41, 0x6d, 0x70, 0x68, 0x65, 0x6e, 0x6f, 0x6c, 0x20, 0x20, 0x20, 0x20,
0x20, 0x20, 0x20, 0x20, 0x0d, 0x78, 0xa7, 0x14, 0x4e, 0x44, 0x43, 0x43, 0x47, 0x46, 0x2d, 0x43,
0x31, 0x30, 0x34, 0x20, 0x20, 0x20, 0x20, 0x20, 0x41, 0x20, 0x20, 0x20, 0x03, 0x00, 0x00, 0x17,
0x00, 0x00, 0x67, 0x00, 0x41, 0x50, 0x46, 0x31, 0x37, 0x31, 0x34, 0x31, 0x30, 0x34, 0x35, 0x55,
0x47, 0x56, 0x20, 0x20, 0x31, 0x37, 0x30, 0x34, 0x30, 0x38, 0x20, 0x20, 0x00, 0x00, 0x08, 0x83,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
},
.info = {
"Amphenol ",
"NDCCGF-C104 ",
"APF17141045UGV ",
SFF_25G_BASE_CR_PROPERTIES,
1,
} ,
},
},
{
{
.eeprom = {
0x03, 0x04, 0x21, 0x01, 0x00, 0x00, 0x04, 0x41, 0x84, 0x80, 0xd5, 0x06, 0xff, 0x00, 0x00, 0x00,
0x00, 0x00, 0x01, 0x00, 0x41, 0x6d, 0x70, 0x68, 0x65, 0x6e, 0x6f, 0x6c, 0x20, 0x20, 0x20, 0x20,
0x20, 0x20, 0x20, 0x20, 0x0b, 0x78, 0xa7, 0x14, 0x4e, 0x44, 0x43, 0x43, 0x47, 0x46, 0x2d, 0x48,
0x33, 0x30, 0x31, 0x20, 0x20, 0x20, 0x20, 0x20, 0x41, 0x20, 0x20, 0x20, 0x01, 0x00, 0x00, 0xaf,
0x00, 0x00, 0x67, 0x00, 0x41, 0x50, 0x46, 0x31, 0x36, 0x34, 0x35, 0x33, 0x30, 0x31, 0x33, 0x33,
0x50, 0x31, 0x20, 0x20, 0x31, 0x36, 0x31, 0x31, 0x31, 0x36, 0x20, 0x20, 0x00, 0x00, 0x08, 0x41,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x01, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x04,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
},
.info = {
"Amphenol ",
"NDCCGF-H301 ",
"APF164530133P1 ",
SFF_25G_BASE_CR_PROPERTIES,
1,
} ,
},
},
{
{
.eeprom = {
0x03, 0x04, 0x21, 0x01, 0x00, 0x00, 0x04, 0x41, 0x84, 0x80, 0xd5, 0x06, 0xff, 0x00, 0x00, 0x00,
0x00, 0x00, 0x03, 0x00, 0x41, 0x6d, 0x70, 0x68, 0x65, 0x6e, 0x6f, 0x6c, 0x20, 0x20, 0x20, 0x20,
0x20, 0x20, 0x20, 0x20, 0x0b, 0x78, 0xa7, 0x14, 0x4e, 0x44, 0x41, 0x51, 0x47, 0x46, 0x2d, 0x48,
0x33, 0x30, 0x33, 0x20, 0x20, 0x20, 0x20, 0x20, 0x41, 0x20, 0x20, 0x20, 0x01, 0x00, 0x00, 0xbf,
0x00, 0x00, 0x67, 0x00, 0x41, 0x50, 0x46, 0x31, 0x36, 0x35, 0x30, 0x33, 0x30, 0x33, 0x31, 0x4c,
0x50, 0x44, 0x20, 0x20, 0x31, 0x36, 0x31, 0x32, 0x31, 0x37, 0x20, 0x20, 0x00, 0x00, 0x08, 0x6b,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x03, 0x00, 0x05, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x08,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
},
.info = {
"Amphenol ",
"NDAQGF-H303 ",
"APF16503031LPD ",
SFF_25G_BASE_CR_PROPERTIES,
3,
},
},
},
{
{
.eeprom = {
0x03, 0x04, 0x23, 0x01, 0x00, 0x00, 0x00, 0x00, 0x84, 0x00, 0x00, 0x06, 0xff, 0x00, 0x00, 0x00,
0x00, 0x00, 0x03, 0x00, 0x41, 0x6d, 0x70, 0x68, 0x65, 0x6e, 0x6f, 0x6c, 0x20, 0x20, 0x20, 0x20,
0x20, 0x20, 0x20, 0x20, 0x00, 0x78, 0xa7, 0x14, 0x4e, 0x44, 0x41, 0x51, 0x47, 0x46, 0x2d, 0x30,
0x30, 0x30, 0x33, 0x20, 0x20, 0x20, 0x20, 0x20, 0x41, 0x20, 0x20, 0x20, 0x01, 0x00, 0x00, 0x01,
0x00, 0x00, 0x67, 0x00, 0x41, 0x50, 0x46, 0x31, 0x36, 0x32, 0x35, 0x30, 0x30, 0x33, 0x31, 0x4b,
0x43, 0x55, 0x20, 0x20, 0x31, 0x36, 0x30, 0x36, 0x32, 0x35, 0x20, 0x20, 0x00, 0x00, 0x08, 0x6f,
0x44, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
},
.info = {
"Amphenol ",
"NDAQGF-0003 ",
"APF16250031KCU ",
SFF_25G_BASE_CR_PROPERTIES,
3,
},
},
},
{
{
.eeprom = {
0x0d, 0x00, 0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x43, 0x4d, 0x50, 0x51, 0x41, 0x41, 0x31, 0x43, 0x41, 0x41, 0x33, 0x37, 0x2d, 0x31,
0x33, 0x32, 0x31, 0x2d, 0x30, 0x32, 0x56, 0x30, 0x32, 0x20, 0x51, 0x53, 0x46, 0x50, 0x2d, 0xe6,
0x53, 0x46, 0x50, 0x31, 0x30, 0x47, 0x2d, 0x43, 0x55, 0x31, 0x4d, 0x20, 0x20, 0x20, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x34,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03,
0x0d, 0x00, 0x23, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x05, 0x67, 0x00, 0x00, 0x00,
0x00, 0x00, 0x01, 0xa0, 0x4f, 0x45, 0x4d, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20,
0x20, 0x20, 0x20, 0x20, 0x00, 0x00, 0x00, 0x00, 0x51, 0x53, 0x46, 0x50, 0x2d, 0x48, 0x34, 0x30,
0x47, 0x2d, 0x43, 0x55, 0x31, 0x4d, 0x2d, 0x43, 0x41, 0x20, 0x00, 0x00, 0x00, 0x00, 0x46, 0x7a,
0x00, 0x00, 0x00, 0x00, 0x45, 0x31, 0x36, 0x31, 0x31, 0x31, 0x36, 0x30, 0x30, 0x36, 0x37, 0x20,
0x20, 0x20, 0x20, 0x20, 0x31, 0x36, 0x31, 0x32, 0x30, 0x32, 0x20, 0x20, 0x00, 0x00, 0xe2, 0x30,
0x00, 0x00, 0x11, 0xbc, 0xb2, 0x5f, 0x4b, 0xf4, 0x39, 0x79, 0xf6, 0xca, 0xb9, 0x62, 0xf7, 0x4c,
0x14, 0xd8, 0x63, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x7d, 0xc5, 0xef, 0x53,
},
.info = {
"OEM ",
"QSFP-H40G-CU1M-C",
"E1611160067 ",
SFF_40G_BASE_CR4_PROPERTIES,
1,
},
},
},
#endif /** SFF_CONFIG_INCLUDE_DATABASE */
};

View File

@@ -224,6 +224,55 @@ static struct i2c_driver as5822_54x_psu_driver = {
.address_list = normal_i2c,
};
static int as5822_54x_psu_read_byte(struct i2c_client *client, u8 command, u8 *data)
{
int status = 0;
int retry_count = 5;
while (retry_count) {
status = i2c_smbus_read_byte_data(client, command);
if (unlikely(status < 0)) {
msleep(10);
retry_count--;
continue;
}
break;
}
if (unlikely(status < 0)) {
dev_dbg(&client->dev, "sfp read byte data failed, command(0x%2x), data(0x%2x)\r\n", command, status);
goto abort;
}
*data = (u8)status;
abort:
return status;
}
static int as5822_54x_psu_read_bytes(struct i2c_client *client, u8 command, u8 *data,
int data_len)
{
int ret = 0;
while (data_len) {
ssize_t status;
status = as5822_54x_psu_read_byte(client, command, data);
if (status <= 0) {
ret = status;
break;
}
data += 1;
command += 1;
data_len -= 1;
}
return ret;
}
static int as5822_54x_psu_read_block(struct i2c_client *client, u8 command, u8 *data,
int data_len)
{
@@ -284,7 +333,7 @@ static struct as5822_54x_psu_data *as5822_54x_psu_update_device(struct device *d
if (IS_PRESENT(data->index, data->status)) {
/* Read model name */
status = as5822_54x_psu_read_block(client, MODEL_NAME_REG_OFFSET, data->model_name,
status = as5822_54x_psu_read_bytes(client, MODEL_NAME_REG_OFFSET, data->model_name,
ARRAY_SIZE(data->model_name)-1);
if (status < 0) {
@@ -300,7 +349,7 @@ static struct as5822_54x_psu_data *as5822_54x_psu_update_device(struct device *d
}
/* Read serial number */
status = as5822_54x_psu_read_block(client, SERIAL_NUM_REG_OFFSET, data->serial,
status = as5822_54x_psu_read_bytes(client, SERIAL_NUM_REG_OFFSET, data->serial,
ARRAY_SIZE(data->serial)-1);
if (status < 0) {

View File

@@ -0,0 +1,3 @@
*x86*64*accton*as7816*64x*.mk
onlpdump.mk

View File

@@ -0,0 +1 @@
include $(ONL)/make/pkg.mk

View File

@@ -0,0 +1 @@
include $(ONL)/make/pkg.mk

View File

@@ -0,0 +1 @@
!include $ONL_TEMPLATES/platform-modules.yml VENDOR=accton BASENAME=x86-64-accton-as7816-64x ARCH=amd64 KERNELS="onl-kernel-3.16-lts-x86-64-all:amd64"

View File

@@ -0,0 +1,6 @@
KERNELS := onl-kernel-3.16-lts-x86-64-all:amd64
KMODULES := $(wildcard *.c)
VENDOR := accton
BASENAME := x86-64-accton-as7816-64x
ARCH := x86_64
include $(ONL)/make/kmodule.mk

View File

@@ -0,0 +1,456 @@
/*
* A hwmon driver for the Accton as7816-64x fan
*
* Copyright (C) 2014 Accton Technology Corporation.
* Brandon Chuang <brandon_chuang@accton.com.tw>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <linux/module.h>
#include <linux/jiffies.h>
#include <linux/i2c.h>
#include <linux/hwmon.h>
#include <linux/hwmon-sysfs.h>
#include <linux/err.h>
#include <linux/mutex.h>
#include <linux/sysfs.h>
#include <linux/slab.h>
#include <linux/dmi.h>
#define DRVNAME "as7816_64x_fan"
static struct as7816_64x_fan_data *as7816_64x_fan_update_device(struct device *dev);
static ssize_t fan_show_value(struct device *dev, struct device_attribute *da, char *buf);
static ssize_t set_duty_cycle(struct device *dev, struct device_attribute *da,
const char *buf, size_t count);
/* fan related data, the index should match sysfs_fan_attributes
*/
static const u8 fan_reg[] = {
0x80, /* fan 1-4 present status */
0x81, /* fan 1-4 direction(0:F2B 1:B2F) */
0x87, /* fan PWM(for all fan) */
0x90, /* front fan 1 speed(rpm) */
0x91, /* front fan 2 speed(rpm) */
0x92, /* front fan 3 speed(rpm) */
0x93, /* front fan 4 speed(rpm) */
0x98, /* rear fan 1 speed(rpm) */
0x99, /* rear fan 2 speed(rpm) */
0x9A, /* rear fan 3 speed(rpm) */
0x9B, /* rear fan 4 speed(rpm) */
};
/* Each client has this additional data */
struct as7816_64x_fan_data {
struct device *hwmon_dev;
struct mutex update_lock;
char valid; /* != 0 if registers are valid */
unsigned long last_updated; /* In jiffies */
u8 reg_val[ARRAY_SIZE(fan_reg)]; /* Register value */
};
enum fan_id {
FAN1_ID,
FAN2_ID,
FAN3_ID,
FAN4_ID
};
enum sysfs_fan_attributes {
FAN_PRESENT_REG,
FAN_DIRECTION_REG,
FAN_DUTY_CYCLE_PERCENTAGE, /* Only one CPLD register to control duty cycle for all fans */
FAN1_FRONT_SPEED_RPM,
FAN2_FRONT_SPEED_RPM,
FAN3_FRONT_SPEED_RPM,
FAN4_FRONT_SPEED_RPM,
FAN1_REAR_SPEED_RPM,
FAN2_REAR_SPEED_RPM,
FAN3_REAR_SPEED_RPM,
FAN4_REAR_SPEED_RPM,
FAN1_DIRECTION,
FAN2_DIRECTION,
FAN3_DIRECTION,
FAN4_DIRECTION,
FAN1_PRESENT,
FAN2_PRESENT,
FAN3_PRESENT,
FAN4_PRESENT,
FAN1_FAULT,
FAN2_FAULT,
FAN3_FAULT,
FAN4_FAULT
};
/* Define attributes
*/
#define DECLARE_FAN_FAULT_SENSOR_DEV_ATTR(index) \
static SENSOR_DEVICE_ATTR(fan##index##_fault, S_IRUGO, fan_show_value, NULL, FAN##index##_FAULT)
#define DECLARE_FAN_FAULT_ATTR(index) &sensor_dev_attr_fan##index##_fault.dev_attr.attr
#define DECLARE_FAN_DIRECTION_SENSOR_DEV_ATTR(index) \
static SENSOR_DEVICE_ATTR(fan##index##_direction, S_IRUGO, fan_show_value, NULL, FAN##index##_DIRECTION)
#define DECLARE_FAN_DIRECTION_ATTR(index) &sensor_dev_attr_fan##index##_direction.dev_attr.attr
#define DECLARE_FAN_DUTY_CYCLE_SENSOR_DEV_ATTR(index) \
static SENSOR_DEVICE_ATTR(fan##index##_duty_cycle_percentage, S_IWUSR | S_IRUGO, fan_show_value, set_duty_cycle, FAN##index##_DUTY_CYCLE_PERCENTAGE)
#define DECLARE_FAN_DUTY_CYCLE_ATTR(index) &sensor_dev_attr_fan##index##_duty_cycle_percentage.dev_attr.attr
#define DECLARE_FAN_PRESENT_SENSOR_DEV_ATTR(index) \
static SENSOR_DEVICE_ATTR(fan##index##_present, S_IRUGO, fan_show_value, NULL, FAN##index##_PRESENT)
#define DECLARE_FAN_PRESENT_ATTR(index) &sensor_dev_attr_fan##index##_present.dev_attr.attr
#define DECLARE_FAN_SPEED_RPM_SENSOR_DEV_ATTR(index) \
static SENSOR_DEVICE_ATTR(fan##index##_front_speed_rpm, S_IRUGO, fan_show_value, NULL, FAN##index##_FRONT_SPEED_RPM);\
static SENSOR_DEVICE_ATTR(fan##index##_rear_speed_rpm, S_IRUGO, fan_show_value, NULL, FAN##index##_REAR_SPEED_RPM)
#define DECLARE_FAN_SPEED_RPM_ATTR(index) &sensor_dev_attr_fan##index##_front_speed_rpm.dev_attr.attr, \
&sensor_dev_attr_fan##index##_rear_speed_rpm.dev_attr.attr
/* 6 fan fault attributes in this platform */
DECLARE_FAN_FAULT_SENSOR_DEV_ATTR(1);
DECLARE_FAN_FAULT_SENSOR_DEV_ATTR(2);
DECLARE_FAN_FAULT_SENSOR_DEV_ATTR(3);
DECLARE_FAN_FAULT_SENSOR_DEV_ATTR(4);
/* 6 fan speed(rpm) attributes in this platform */
DECLARE_FAN_SPEED_RPM_SENSOR_DEV_ATTR(1);
DECLARE_FAN_SPEED_RPM_SENSOR_DEV_ATTR(2);
DECLARE_FAN_SPEED_RPM_SENSOR_DEV_ATTR(3);
DECLARE_FAN_SPEED_RPM_SENSOR_DEV_ATTR(4);
/* 6 fan present attributes in this platform */
DECLARE_FAN_PRESENT_SENSOR_DEV_ATTR(1);
DECLARE_FAN_PRESENT_SENSOR_DEV_ATTR(2);
DECLARE_FAN_PRESENT_SENSOR_DEV_ATTR(3);
DECLARE_FAN_PRESENT_SENSOR_DEV_ATTR(4);
/* 6 fan direction attribute in this platform */
DECLARE_FAN_DIRECTION_SENSOR_DEV_ATTR(1);
DECLARE_FAN_DIRECTION_SENSOR_DEV_ATTR(2);
DECLARE_FAN_DIRECTION_SENSOR_DEV_ATTR(3);
DECLARE_FAN_DIRECTION_SENSOR_DEV_ATTR(4);
/* 1 fan duty cycle attribute in this platform */
DECLARE_FAN_DUTY_CYCLE_SENSOR_DEV_ATTR();
static struct attribute *as7816_64x_fan_attributes[] = {
/* fan related attributes */
DECLARE_FAN_FAULT_ATTR(1),
DECLARE_FAN_FAULT_ATTR(2),
DECLARE_FAN_FAULT_ATTR(3),
DECLARE_FAN_FAULT_ATTR(4),
DECLARE_FAN_SPEED_RPM_ATTR(1),
DECLARE_FAN_SPEED_RPM_ATTR(2),
DECLARE_FAN_SPEED_RPM_ATTR(3),
DECLARE_FAN_SPEED_RPM_ATTR(4),
DECLARE_FAN_PRESENT_ATTR(1),
DECLARE_FAN_PRESENT_ATTR(2),
DECLARE_FAN_PRESENT_ATTR(3),
DECLARE_FAN_PRESENT_ATTR(4),
DECLARE_FAN_DIRECTION_ATTR(1),
DECLARE_FAN_DIRECTION_ATTR(2),
DECLARE_FAN_DIRECTION_ATTR(3),
DECLARE_FAN_DIRECTION_ATTR(4),
DECLARE_FAN_DUTY_CYCLE_ATTR(),
NULL
};
#define FAN_DUTY_CYCLE_REG_MASK 0xF
#define FAN_MAX_DUTY_CYCLE 100
#define FAN_REG_VAL_TO_SPEED_RPM_STEP 100
static int as7816_64x_fan_read_value(struct i2c_client *client, u8 reg)
{
return i2c_smbus_read_byte_data(client, reg);
}
static int as7816_64x_fan_write_value(struct i2c_client *client, u8 reg, u8 value)
{
return i2c_smbus_write_byte_data(client, reg, value);
}
/* fan utility functions
*/
static u32 reg_val_to_duty_cycle(u8 reg_val)
{
reg_val &= FAN_DUTY_CYCLE_REG_MASK;
if (!reg_val) {
return 0;
}
if (reg_val == 0xF) {
return FAN_MAX_DUTY_CYCLE;
}
return (reg_val * 6) + 10;
}
static u8 duty_cycle_to_reg_val(u8 duty_cycle)
{
if (duty_cycle < 16) {
return 0;
}
if (duty_cycle >= 100) {
return 0xF;
}
return (duty_cycle - 10) / 6;
}
static u32 reg_val_to_speed_rpm(u8 reg_val)
{
return (u32)reg_val * FAN_REG_VAL_TO_SPEED_RPM_STEP;
}
static u8 reg_val_to_direction(u8 reg_val, enum fan_id id)
{
u8 mask = (1 << id);
return !!(reg_val & mask);
}
static u8 reg_val_to_is_present(u8 reg_val, enum fan_id id)
{
u8 mask = (1 << id);
return !(reg_val & mask);
}
static u8 is_fan_fault(struct as7816_64x_fan_data *data, enum fan_id id)
{
u8 ret = 1;
int front_fan_index = FAN1_FRONT_SPEED_RPM + id;
int rear_fan_index = FAN1_REAR_SPEED_RPM + id;
/* Check if the speed of front or rear fan is ZERO,
*/
if (reg_val_to_speed_rpm(data->reg_val[front_fan_index]) &&
reg_val_to_speed_rpm(data->reg_val[rear_fan_index])) {
ret = 0;
}
return ret;
}
static ssize_t set_duty_cycle(struct device *dev, struct device_attribute *da,
const char *buf, size_t count)
{
int error, value;
struct i2c_client *client = to_i2c_client(dev);
error = kstrtoint(buf, 10, &value);
if (error)
return error;
if (value < 0 || value > FAN_MAX_DUTY_CYCLE)
return -EINVAL;
as7816_64x_fan_write_value(client, 0x28, 0); /* Disable fan speed watch dog */
as7816_64x_fan_write_value(client, fan_reg[FAN_DUTY_CYCLE_PERCENTAGE], duty_cycle_to_reg_val(value));
return count;
}
static ssize_t fan_show_value(struct device *dev, struct device_attribute *da,
char *buf)
{
struct sensor_device_attribute *attr = to_sensor_dev_attr(da);
struct as7816_64x_fan_data *data = as7816_64x_fan_update_device(dev);
ssize_t ret = 0;
if (data->valid) {
switch (attr->index) {
case FAN_DUTY_CYCLE_PERCENTAGE:
{
u32 duty_cycle = reg_val_to_duty_cycle(data->reg_val[FAN_DUTY_CYCLE_PERCENTAGE]);
ret = sprintf(buf, "%u\n", duty_cycle);
break;
}
case FAN1_FRONT_SPEED_RPM:
case FAN2_FRONT_SPEED_RPM:
case FAN3_FRONT_SPEED_RPM:
case FAN4_FRONT_SPEED_RPM:
case FAN1_REAR_SPEED_RPM:
case FAN2_REAR_SPEED_RPM:
case FAN3_REAR_SPEED_RPM:
case FAN4_REAR_SPEED_RPM:
{
ret = sprintf(buf, "%u\n", reg_val_to_speed_rpm(data->reg_val[attr->index]));
break;
}
case FAN1_PRESENT:
case FAN2_PRESENT:
case FAN3_PRESENT:
case FAN4_PRESENT:
ret = sprintf(buf, "%d\n",
reg_val_to_is_present(data->reg_val[FAN_PRESENT_REG],
attr->index - FAN1_PRESENT));
break;
case FAN1_FAULT:
case FAN2_FAULT:
case FAN3_FAULT:
case FAN4_FAULT:
ret = sprintf(buf, "%d\n", is_fan_fault(data, attr->index - FAN1_FAULT));
break;
case FAN1_DIRECTION:
case FAN2_DIRECTION:
case FAN3_DIRECTION:
case FAN4_DIRECTION:
ret = sprintf(buf, "%d\n",
reg_val_to_direction(data->reg_val[FAN_DIRECTION_REG],
attr->index - FAN1_DIRECTION));
break;
default:
break;
}
}
return ret;
}
static const struct attribute_group as7816_64x_fan_group = {
.attrs = as7816_64x_fan_attributes,
};
static struct as7816_64x_fan_data *as7816_64x_fan_update_device(struct device *dev)
{
struct i2c_client *client = to_i2c_client(dev);
struct as7816_64x_fan_data *data = i2c_get_clientdata(client);
mutex_lock(&data->update_lock);
if (time_after(jiffies, data->last_updated + HZ + HZ / 2) ||
!data->valid) {
int i;
dev_dbg(&client->dev, "Starting as7816_64x_fan update\n");
data->valid = 0;
/* Update fan data
*/
for (i = 0; i < ARRAY_SIZE(data->reg_val); i++) {
int status = as7816_64x_fan_read_value(client, fan_reg[i]);
if (status < 0) {
data->valid = 0;
mutex_unlock(&data->update_lock);
dev_dbg(&client->dev, "reg %d, err %d\n", fan_reg[i], status);
return data;
}
else {
data->reg_val[i] = status;
}
}
data->last_updated = jiffies;
data->valid = 1;
}
mutex_unlock(&data->update_lock);
return data;
}
static int as7816_64x_fan_probe(struct i2c_client *client,
const struct i2c_device_id *dev_id)
{
struct as7816_64x_fan_data *data;
int status;
if (!i2c_check_functionality(client->adapter, I2C_FUNC_SMBUS_BYTE_DATA)) {
status = -EIO;
goto exit;
}
data = kzalloc(sizeof(struct as7816_64x_fan_data), GFP_KERNEL);
if (!data) {
status = -ENOMEM;
goto exit;
}
i2c_set_clientdata(client, data);
data->valid = 0;
mutex_init(&data->update_lock);
dev_info(&client->dev, "chip found\n");
/* Register sysfs hooks */
status = sysfs_create_group(&client->dev.kobj, &as7816_64x_fan_group);
if (status) {
goto exit_free;
}
data->hwmon_dev = hwmon_device_register(&client->dev);
if (IS_ERR(data->hwmon_dev)) {
status = PTR_ERR(data->hwmon_dev);
goto exit_remove;
}
dev_info(&client->dev, "%s: fan '%s'\n",
dev_name(data->hwmon_dev), client->name);
return 0;
exit_remove:
sysfs_remove_group(&client->dev.kobj, &as7816_64x_fan_group);
exit_free:
kfree(data);
exit:
return status;
}
static int as7816_64x_fan_remove(struct i2c_client *client)
{
struct as7816_64x_fan_data *data = i2c_get_clientdata(client);
hwmon_device_unregister(data->hwmon_dev);
sysfs_remove_group(&client->dev.kobj, &as7816_64x_fan_group);
return 0;
}
/* Addresses to scan */
static const unsigned short normal_i2c[] = { I2C_CLIENT_END };
static const struct i2c_device_id as7816_64x_fan_id[] = {
{ "as7816_64x_fan", 0 },
{}
};
MODULE_DEVICE_TABLE(i2c, as7816_64x_fan_id);
static struct i2c_driver as7816_64x_fan_driver = {
.class = I2C_CLASS_HWMON,
.driver = {
.name = DRVNAME,
},
.probe = as7816_64x_fan_probe,
.remove = as7816_64x_fan_remove,
.id_table = as7816_64x_fan_id,
.address_list = normal_i2c,
};
static int __init as7816_64x_fan_init(void)
{
return i2c_add_driver(&as7816_64x_fan_driver);
}
static void __exit as7816_64x_fan_exit(void)
{
i2c_del_driver(&as7816_64x_fan_driver);
}
module_init(as7816_64x_fan_init);
module_exit(as7816_64x_fan_exit);
MODULE_AUTHOR("Brandon Chuang <brandon_chuang@accton.com.tw>");
MODULE_DESCRIPTION("as7816_64x_fan driver");
MODULE_LICENSE("GPL");

View File

@@ -0,0 +1,460 @@
/*
* A LED driver for the as7816_64x_led
*
* Copyright (C) 2014 Accton Technology Corporation.
* Brandon Chuang <brandon_chuang@accton.com.tw>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
/*#define DEBUG*/
#include <linux/module.h>
#include <linux/kernel.h>
#include <linux/init.h>
#include <linux/platform_device.h>
#include <linux/err.h>
#include <linux/leds.h>
#include <linux/slab.h>
#include <linux/dmi.h>
extern int accton_i2c_cpld_read (unsigned short cpld_addr, u8 reg);
extern int accton_i2c_cpld_write(unsigned short cpld_addr, u8 reg, u8 value);
extern void led_classdev_unregister(struct led_classdev *led_cdev);
extern int led_classdev_register(struct device *parent, struct led_classdev *led_cdev);
extern void led_classdev_resume(struct led_classdev *led_cdev);
extern void led_classdev_suspend(struct led_classdev *led_cdev);
#define DRVNAME "as7816_64x_led"
struct as7816_64x_led_data {
struct platform_device *pdev;
struct mutex update_lock;
char valid; /* != 0 if registers are valid */
unsigned long last_updated; /* In jiffies */
u8 reg_val[1]; /* only 1 register*/
};
static struct as7816_64x_led_data *ledctl = NULL;
/* LED related data
*/
#define LED_CNTRLER_I2C_ADDRESS (0x60)
#define LED_TYPE_DIAG_REG_MASK (0x03)
#define LED_MODE_DIAG_YELLOW_VALUE (0x00)
#define LED_MODE_DIAG_RED_VALUE (0x01)
#define LED_MODE_DIAG_GREEN_VALUE (0x02)
#define LED_MODE_DIAG_OFF_VALUE (0x03)
#define LED_TYPE_LOC_REG_MASK (0x10)
#define LED_MODE_LOC_ORANGE_VALUE (0x00)
#define LED_MODE_LOC_OFF_VALUE (0x10)
#define LED_TYPE_FAN_REG_MASK (0x0C)
#define LED_MODE_FAN_ORANGE_VALUE (0x04)
#define LED_MODE_FAN_GREEN_VALUE_1 (0x00)
#define LED_MODE_FAN_GREEN_VALUE_2 (0x08)
#define LED_MODE_FAN_OFF_VALUE (0x0C)
enum led_type {
LED_TYPE_DIAG,
LED_TYPE_LOC,
LED_TYPE_FAN,
LED_TYPE_PSU1,
LED_TYPE_PSU2
};
struct led_reg {
u32 types;
u8 reg_addr;
};
static const struct led_reg led_reg_map[] = {
{(1 << LED_TYPE_LOC) | (1 << LED_TYPE_DIAG) | (1 << LED_TYPE_FAN), 0x30},
};
enum led_light_mode {
LED_MODE_OFF,
LED_MODE_RED = 10,
LED_MODE_RED_BLINKING = 11,
LED_MODE_ORANGE = 12,
LED_MODE_ORANGE_BLINKING = 13,
LED_MODE_YELLOW = 14,
LED_MODE_YELLOW_BLINKING = 15,
LED_MODE_GREEN = 16,
LED_MODE_GREEN_BLINKING = 17,
LED_MODE_BLUE = 18,
LED_MODE_BLUE_BLINKING = 19,
LED_MODE_PURPLE = 20,
LED_MODE_PURPLE_BLINKING = 21,
LED_MODE_AUTO = 22,
LED_MODE_AUTO_BLINKING = 23,
LED_MODE_WHITE = 24,
LED_MODE_WHITE_BLINKING = 25,
LED_MODE_CYAN = 26,
LED_MODE_CYAN_BLINKING = 27,
LED_MODE_UNKNOWN = 99
};
struct led_type_mode {
enum led_type type;
enum led_light_mode mode;
int reg_bit_mask;
int mode_value;
};
static struct led_type_mode led_type_mode_data[] = {
{LED_TYPE_LOC, LED_MODE_OFF, LED_TYPE_LOC_REG_MASK, LED_MODE_LOC_OFF_VALUE},
{LED_TYPE_LOC, LED_MODE_ORANGE,LED_TYPE_LOC_REG_MASK, LED_MODE_LOC_ORANGE_VALUE},
{LED_TYPE_DIAG, LED_MODE_OFF, LED_TYPE_DIAG_REG_MASK, LED_MODE_DIAG_OFF_VALUE},
{LED_TYPE_DIAG, LED_MODE_GREEN, LED_TYPE_DIAG_REG_MASK, LED_MODE_DIAG_GREEN_VALUE},
{LED_TYPE_DIAG, LED_MODE_RED, LED_TYPE_DIAG_REG_MASK, LED_MODE_DIAG_RED_VALUE},
{LED_TYPE_DIAG, LED_MODE_YELLOW,LED_TYPE_DIAG_REG_MASK, LED_MODE_DIAG_YELLOW_VALUE},
{LED_TYPE_FAN, LED_MODE_OFF, LED_TYPE_FAN_REG_MASK, LED_MODE_FAN_OFF_VALUE},
{LED_TYPE_FAN, LED_MODE_GREEN, LED_TYPE_FAN_REG_MASK, LED_MODE_FAN_GREEN_VALUE_1},
{LED_TYPE_FAN, LED_MODE_GREEN, LED_TYPE_FAN_REG_MASK, LED_MODE_FAN_GREEN_VALUE_2},
{LED_TYPE_FAN, LED_MODE_ORANGE,LED_TYPE_FAN_REG_MASK, LED_MODE_FAN_ORANGE_VALUE}
};
static int get_led_reg(enum led_type type, u8 *reg)
{
int i;
for (i = 0; i < ARRAY_SIZE(led_reg_map); i++) {
if(led_reg_map[i].types & (1 << type)) {
*reg = led_reg_map[i].reg_addr;
return 0;
}
}
return 1;
}
static int led_reg_val_to_light_mode(enum led_type type, u8 reg_val)
{
int i;
for (i = 0; i < ARRAY_SIZE(led_type_mode_data); i++) {
if (type != led_type_mode_data[i].type)
continue;
if ((led_type_mode_data[i].reg_bit_mask & reg_val) ==
led_type_mode_data[i].mode_value)
{
return led_type_mode_data[i].mode;
}
}
return 0;
}
static u8 led_light_mode_to_reg_val(enum led_type type,
enum led_light_mode mode, u8 reg_val) {
int i;
for (i = 0; i < ARRAY_SIZE(led_type_mode_data); i++) {
if (type != led_type_mode_data[i].type)
continue;
if (mode != led_type_mode_data[i].mode)
continue;
reg_val = led_type_mode_data[i].mode_value |
(reg_val & (~led_type_mode_data[i].reg_bit_mask));
break;
}
return reg_val;
}
static int as7816_64x_led_read_value(u8 reg)
{
return accton_i2c_cpld_read(LED_CNTRLER_I2C_ADDRESS, reg);
}
static int as7816_64x_led_write_value(u8 reg, u8 value)
{
return accton_i2c_cpld_write(LED_CNTRLER_I2C_ADDRESS, reg, value);
}
static void as7816_64x_led_update(void)
{
mutex_lock(&ledctl->update_lock);
if (time_after(jiffies, ledctl->last_updated + HZ + HZ / 2)
|| !ledctl->valid) {
int i;
dev_dbg(&ledctl->pdev->dev, "Starting as7816_64x_led update\n");
/* Update LED data
*/
for (i = 0; i < ARRAY_SIZE(ledctl->reg_val); i++) {
int status = as7816_64x_led_read_value(led_reg_map[i].reg_addr);
if (status < 0) {
ledctl->valid = 0;
dev_dbg(&ledctl->pdev->dev, "reg %d, err %d\n", led_reg_map[i].reg_addr, status);
goto exit;
}
else
{
ledctl->reg_val[i] = status;
}
}
ledctl->last_updated = jiffies;
ledctl->valid = 1;
}
exit:
mutex_unlock(&ledctl->update_lock);
}
static void as7816_64x_led_set(struct led_classdev *led_cdev,
enum led_brightness led_light_mode,
enum led_type type)
{
int reg_val;
u8 reg ;
mutex_lock(&ledctl->update_lock);
if( !get_led_reg(type, &reg)) {
dev_dbg(&ledctl->pdev->dev, "Not match register for %d.\n", type);
}
reg_val = as7816_64x_led_read_value(reg);
if (reg_val < 0) {
dev_dbg(&ledctl->pdev->dev, "reg %d, err %d\n", reg, reg_val);
goto exit;
}
reg_val = led_light_mode_to_reg_val(type, led_light_mode, reg_val);
as7816_64x_led_write_value(reg, reg_val);
/* to prevent the slow-update issue */
ledctl->valid = 0;
exit:
mutex_unlock(&ledctl->update_lock);
}
static void as7816_64x_led_diag_set(struct led_classdev *led_cdev,
enum led_brightness led_light_mode)
{
as7816_64x_led_set(led_cdev, led_light_mode, LED_TYPE_DIAG);
}
static enum led_brightness as7816_64x_led_diag_get(struct led_classdev *cdev)
{
as7816_64x_led_update();
return led_reg_val_to_light_mode(LED_TYPE_DIAG, ledctl->reg_val[0]);
}
static void as7816_64x_led_loc_set(struct led_classdev *led_cdev,
enum led_brightness led_light_mode)
{
as7816_64x_led_set(led_cdev, led_light_mode, LED_TYPE_LOC);
}
static enum led_brightness as7816_64x_led_loc_get(struct led_classdev *cdev)
{
as7816_64x_led_update();
return led_reg_val_to_light_mode(LED_TYPE_LOC, ledctl->reg_val[0]);
}
static void as7816_64x_led_fan_set(struct led_classdev *led_cdev,
enum led_brightness led_light_mode)
{
as7816_64x_led_set(led_cdev, led_light_mode, LED_TYPE_FAN);
}
static enum led_brightness as7816_64x_led_fan_get(struct led_classdev *cdev)
{
as7816_64x_led_update();
return led_reg_val_to_light_mode(LED_TYPE_FAN, ledctl->reg_val[0]);
}
static void as7816_64x_led_auto_set(struct led_classdev *led_cdev,
enum led_brightness led_light_mode)
{
}
static enum led_brightness as7816_64x_led_auto_get(struct led_classdev *cdev)
{
return LED_MODE_AUTO;
}
static struct led_classdev as7816_64x_leds[] = {
[LED_TYPE_DIAG] = {
.name = "as7816_64x_led::diag",
.default_trigger = "unused",
.brightness_set = as7816_64x_led_diag_set,
.brightness_get = as7816_64x_led_diag_get,
.flags = LED_CORE_SUSPENDRESUME,
.max_brightness = LED_MODE_GREEN,
},
[LED_TYPE_LOC] = {
.name = "as7816_64x_led::loc",
.default_trigger = "unused",
.brightness_set = as7816_64x_led_loc_set,
.brightness_get = as7816_64x_led_loc_get,
.flags = LED_CORE_SUSPENDRESUME,
.max_brightness = LED_MODE_ORANGE,
},
[LED_TYPE_FAN] = {
.name = "as7816_64x_led::fan",
.default_trigger = "unused",
.brightness_set = as7816_64x_led_fan_set,
.brightness_get = as7816_64x_led_fan_get,
.flags = LED_CORE_SUSPENDRESUME,
.max_brightness = LED_MODE_GREEN,
},
[LED_TYPE_PSU1] = {
.name = "as7816_64x_led::psu1",
.default_trigger = "unused",
.brightness_set = as7816_64x_led_auto_set,
.brightness_get = as7816_64x_led_auto_get,
.flags = LED_CORE_SUSPENDRESUME,
.max_brightness = LED_MODE_AUTO,
},
[LED_TYPE_PSU2] = {
.name = "as7816_64x_led::psu2",
.default_trigger = "unused",
.brightness_set = as7816_64x_led_auto_set,
.brightness_get = as7816_64x_led_auto_get,
.flags = LED_CORE_SUSPENDRESUME,
.max_brightness = LED_MODE_AUTO,
},
};
static int as7816_64x_led_suspend(struct platform_device *dev,
pm_message_t state)
{
int i = 0;
for (i = 0; i < ARRAY_SIZE(as7816_64x_leds); i++) {
led_classdev_suspend(&as7816_64x_leds[i]);
}
return 0;
}
static int as7816_64x_led_resume(struct platform_device *dev)
{
int i = 0;
for (i = 0; i < ARRAY_SIZE(as7816_64x_leds); i++) {
led_classdev_resume(&as7816_64x_leds[i]);
}
return 0;
}
static int as7816_64x_led_probe(struct platform_device *pdev)
{
int ret, i;
for (i = 0; i < ARRAY_SIZE(as7816_64x_leds); i++) {
ret = led_classdev_register(&pdev->dev, &as7816_64x_leds[i]);
if (ret < 0)
break;
}
/* Check if all LEDs were successfully registered */
if (i != ARRAY_SIZE(as7816_64x_leds)){
int j;
/* only unregister the LEDs that were successfully registered */
for (j = 0; j < i; j++) {
led_classdev_unregister(&as7816_64x_leds[i]);
}
}
return ret;
}
static int as7816_64x_led_remove(struct platform_device *pdev)
{
int i;
for (i = 0; i < ARRAY_SIZE(as7816_64x_leds); i++) {
led_classdev_unregister(&as7816_64x_leds[i]);
}
return 0;
}
static struct platform_driver as7816_64x_led_driver = {
.probe = as7816_64x_led_probe,
.remove = as7816_64x_led_remove,
.suspend = as7816_64x_led_suspend,
.resume = as7816_64x_led_resume,
.driver = {
.name = DRVNAME,
.owner = THIS_MODULE,
},
};
static int __init as7816_64x_led_init(void)
{
int ret;
ret = platform_driver_register(&as7816_64x_led_driver);
if (ret < 0) {
goto exit;
}
ledctl = kzalloc(sizeof(struct as7816_64x_led_data), GFP_KERNEL);
if (!ledctl) {
ret = -ENOMEM;
platform_driver_unregister(&as7816_64x_led_driver);
goto exit;
}
mutex_init(&ledctl->update_lock);
ledctl->pdev = platform_device_register_simple(DRVNAME, -1, NULL, 0);
if (IS_ERR(ledctl->pdev)) {
ret = PTR_ERR(ledctl->pdev);
platform_driver_unregister(&as7816_64x_led_driver);
kfree(ledctl);
goto exit;
}
exit:
return ret;
}
static void __exit as7816_64x_led_exit(void)
{
platform_device_unregister(ledctl->pdev);
platform_driver_unregister(&as7816_64x_led_driver);
kfree(ledctl);
}
module_init(as7816_64x_led_init);
module_exit(as7816_64x_led_exit);
MODULE_AUTHOR("Brandon Chuang <brandon_chuang@accton.com.tw>");
MODULE_DESCRIPTION("as7816_64x_led driver");
MODULE_LICENSE("GPL");

View File

@@ -0,0 +1,239 @@
/*
* An hwmon driver for accton as7816_64x Power Module
*
* Copyright (C) 2014 Accton Technology Corporation.
* Brandon Chuang <brandon_chuang@accton.com.tw>
*
* Based on ad7414.c
* Copyright 2006 Stefan Roese <sr at denx.de>, DENX Software Engineering
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <linux/module.h>
#include <linux/jiffies.h>
#include <linux/i2c.h>
#include <linux/hwmon.h>
#include <linux/hwmon-sysfs.h>
#include <linux/err.h>
#include <linux/mutex.h>
#include <linux/sysfs.h>
#include <linux/slab.h>
#include <linux/delay.h>
#include <linux/dmi.h>
#define PSU_STATUS_I2C_ADDR 0x60
#define PSU_STATUS_I2C_REG_OFFSET 0x03
#define IS_POWER_GOOD(id, value) (!!(value & BIT(2+id)))
#define IS_PRESENT(id, value) (!(value & BIT(id)))
static ssize_t show_status(struct device *dev, struct device_attribute *da, char *buf);
static struct as7816_64x_psu_data *as7816_64x_psu_update_device(struct device *dev);
extern int accton_i2c_cpld_read (unsigned short cpld_addr, u8 reg);
/* Addresses scanned
*/
static const unsigned short normal_i2c[] = { I2C_CLIENT_END };
/* Each client has this additional data
*/
struct as7816_64x_psu_data {
struct device *hwmon_dev;
struct mutex update_lock;
char valid; /* !=0 if registers are valid */
unsigned long last_updated; /* In jiffies */
u8 index; /* PSU index */
u8 status; /* Status(present/power_good) register read from CPLD */
};
enum as7816_64x_psu_sysfs_attributes {
PSU_PRESENT,
PSU_POWER_GOOD
};
/* sysfs attributes for hwmon
*/
static SENSOR_DEVICE_ATTR(psu_present, S_IRUGO, show_status, NULL, PSU_PRESENT);
static SENSOR_DEVICE_ATTR(psu_power_good, S_IRUGO, show_status, NULL, PSU_POWER_GOOD);
static struct attribute *as7816_64x_psu_attributes[] = {
&sensor_dev_attr_psu_present.dev_attr.attr,
&sensor_dev_attr_psu_power_good.dev_attr.attr,
NULL
};
static ssize_t show_status(struct device *dev, struct device_attribute *da,
char *buf)
{
struct sensor_device_attribute *attr = to_sensor_dev_attr(da);
struct as7816_64x_psu_data *data = as7816_64x_psu_update_device(dev);
u8 status = 0;
if (!data->valid) {
return -EIO;
}
if (attr->index == PSU_PRESENT) {
status = IS_PRESENT(data->index, data->status);
}
else { /* PSU_POWER_GOOD */
status = IS_POWER_GOOD(data->index, data->status);
}
return sprintf(buf, "%d\n", status);
}
static const struct attribute_group as7816_64x_psu_group = {
.attrs = as7816_64x_psu_attributes,
};
static int as7816_64x_psu_probe(struct i2c_client *client,
const struct i2c_device_id *dev_id)
{
struct as7816_64x_psu_data *data;
int status;
if (!i2c_check_functionality(client->adapter, I2C_FUNC_SMBUS_I2C_BLOCK)) {
status = -EIO;
goto exit;
}
data = kzalloc(sizeof(struct as7816_64x_psu_data), GFP_KERNEL);
if (!data) {
status = -ENOMEM;
goto exit;
}
i2c_set_clientdata(client, data);
data->valid = 0;
data->index = dev_id->driver_data;
mutex_init(&data->update_lock);
dev_info(&client->dev, "chip found\n");
/* Register sysfs hooks */
status = sysfs_create_group(&client->dev.kobj, &as7816_64x_psu_group);
if (status) {
goto exit_free;
}
data->hwmon_dev = hwmon_device_register(&client->dev);
if (IS_ERR(data->hwmon_dev)) {
status = PTR_ERR(data->hwmon_dev);
goto exit_remove;
}
dev_info(&client->dev, "%s: psu '%s'\n",
dev_name(data->hwmon_dev), client->name);
return 0;
exit_remove:
sysfs_remove_group(&client->dev.kobj, &as7816_64x_psu_group);
exit_free:
kfree(data);
exit:
return status;
}
static int as7816_64x_psu_remove(struct i2c_client *client)
{
struct as7816_64x_psu_data *data = i2c_get_clientdata(client);
hwmon_device_unregister(data->hwmon_dev);
sysfs_remove_group(&client->dev.kobj, &as7816_64x_psu_group);
kfree(data);
return 0;
}
enum psu_index
{
as7816_64x_psu1,
as7816_64x_psu2
};
static const struct i2c_device_id as7816_64x_psu_id[] = {
{ "as7816_64x_psu1", as7816_64x_psu1 },
{ "as7816_64x_psu2", as7816_64x_psu2 },
{}
};
MODULE_DEVICE_TABLE(i2c, as7816_64x_psu_id);
static struct i2c_driver as7816_64x_psu_driver = {
.class = I2C_CLASS_HWMON,
.driver = {
.name = "as7816_64x_psu",
},
.probe = as7816_64x_psu_probe,
.remove = as7816_64x_psu_remove,
.id_table = as7816_64x_psu_id,
.address_list = normal_i2c,
};
static struct as7816_64x_psu_data *as7816_64x_psu_update_device(struct device *dev)
{
struct i2c_client *client = to_i2c_client(dev);
struct as7816_64x_psu_data *data = i2c_get_clientdata(client);
mutex_lock(&data->update_lock);
if (time_after(jiffies, data->last_updated + HZ + HZ / 2)
|| !data->valid) {
int status;
data->valid = 0;
dev_dbg(&client->dev, "Starting as7816_64x update\n");
/* Read psu status */
status = accton_i2c_cpld_read(PSU_STATUS_I2C_ADDR, PSU_STATUS_I2C_REG_OFFSET);
if (status < 0) {
dev_dbg(&client->dev, "cpld reg (0x%x) err %d\n", PSU_STATUS_I2C_ADDR, status);
goto exit;
}
else {
data->status = status;
}
data->last_updated = jiffies;
data->valid = 1;
}
exit:
mutex_unlock(&data->update_lock);
return data;
}
static int __init as7816_64x_psu_init(void)
{
return i2c_add_driver(&as7816_64x_psu_driver);
}
static void __exit as7816_64x_psu_exit(void)
{
i2c_del_driver(&as7816_64x_psu_driver);
}
module_init(as7816_64x_psu_init);
module_exit(as7816_64x_psu_exit);
MODULE_AUTHOR("Brandon Chuang <brandon_chuang@accton.com.tw>");
MODULE_DESCRIPTION("as7816_64x_psu driver");
MODULE_LICENSE("GPL");

View File

@@ -0,0 +1 @@
include $(ONL)/make/pkg.mk

View File

@@ -0,0 +1 @@
!include $ONL_TEMPLATES/onlp-platform-any.yml PLATFORM=x86-64-accton-as7816-64x ARCH=amd64 TOOLCHAIN=x86_64-linux-gnu

View File

@@ -0,0 +1,2 @@
FILTER=src
include $(ONL)/make/subdirs.mk

View File

@@ -0,0 +1,45 @@
############################################################
# <bsn.cl fy=2014 v=onl>
#
# Copyright 2014 BigSwitch Networks, Inc.
#
# Licensed under the Eclipse Public License, Version 1.0 (the
# "License"); you may not use this file except in compliance
# with the License. You may obtain a copy of the License at
#
# http://www.eclipse.org/legal/epl-v10.html
#
# Unless required by applicable law or agreed to in writing,
# software distributed under the License is distributed on an
# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND,
# either express or implied. See the License for the specific
# language governing permissions and limitations under the
# License.
#
# </bsn.cl>
############################################################
#
#
############################################################
include $(ONL)/make/config.amd64.mk
MODULE := libonlp-x86-64-accton-as7816-64x
include $(BUILDER)/standardinit.mk
DEPENDMODULES := AIM IOF x86_64_accton_as7816_64x onlplib
DEPENDMODULE_HEADERS := sff
include $(BUILDER)/dependmodules.mk
SHAREDLIB := libonlp-x86-64-accton-as7816-64x.so
$(SHAREDLIB)_TARGETS := $(ALL_TARGETS)
include $(BUILDER)/so.mk
.DEFAULT_GOAL := $(SHAREDLIB)
GLOBAL_CFLAGS += -I$(onlp_BASEDIR)/module/inc
GLOBAL_CFLAGS += -DAIM_CONFIG_INCLUDE_MODULES_INIT=1
GLOBAL_CFLAGS += -fPIC
GLOBAL_LINK_LIBS += -lpthread
include $(BUILDER)/targets.mk

View File

@@ -0,0 +1,46 @@
############################################################
# <bsn.cl fy=2014 v=onl>
#
# Copyright 2014 BigSwitch Networks, Inc.
#
# Licensed under the Eclipse Public License, Version 1.0 (the
# "License"); you may not use this file except in compliance
# with the License. You may obtain a copy of the License at
#
# http://www.eclipse.org/legal/epl-v10.html
#
# Unless required by applicable law or agreed to in writing,
# software distributed under the License is distributed on an
# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND,
# either express or implied. See the License for the specific
# language governing permissions and limitations under the
# License.
#
# </bsn.cl>
############################################################
#
#
#
############################################################
include $(ONL)/make/config.amd64.mk
.DEFAULT_GOAL := onlpdump
MODULE := onlpdump
include $(BUILDER)/standardinit.mk
DEPENDMODULES := AIM IOF onlp x86_64_accton_as7816_64x onlplib onlp_platform_defaults sff cjson cjson_util timer_wheel OS
include $(BUILDER)/dependmodules.mk
BINARY := onlpdump
$(BINARY)_LIBRARIES := $(LIBRARY_TARGETS)
include $(BUILDER)/bin.mk
GLOBAL_CFLAGS += -DAIM_CONFIG_AIM_MAIN_FUNCTION=onlpdump_main
GLOBAL_CFLAGS += -DAIM_CONFIG_INCLUDE_MODULES_INIT=1
GLOBAL_CFLAGS += -DAIM_CONFIG_INCLUDE_MAIN=1
GLOBAL_LINK_LIBS += -lpthread -lm
include $(BUILDER)/targets.mk

View File

@@ -0,0 +1 @@
name: x86_64_accton_as7816_64x

View File

@@ -0,0 +1,9 @@
###############################################################################
#
#
#
###############################################################################
include ../../init.mk
MODULE := x86_64_accton_as7816_64x
AUTOMODULE := x86_64_accton_as7816_64x
include $(BUILDER)/definemodule.mk

View File

@@ -0,0 +1,6 @@
###############################################################################
#
# x86_64_accton_as7816_64x README
#
###############################################################################

View File

@@ -0,0 +1,9 @@
###############################################################################
#
# x86_64_accton_as7816_64x Autogeneration
#
###############################################################################
x86_64_accton_as7816_64x_AUTO_DEFS := module/auto/x86_64_accton_as7816_64x.yml
x86_64_accton_as7816_64x_AUTO_DIRS := module/inc/x86_64_accton_as7816_64x module/src
include $(BUILDER)/auto.mk

View File

@@ -0,0 +1,50 @@
###############################################################################
#
# x86_64_accton_as7816_64x Autogeneration Definitions.
#
###############################################################################
cdefs: &cdefs
- X86_64_ACCTON_AS7816_64X_CONFIG_INCLUDE_LOGGING:
doc: "Include or exclude logging."
default: 1
- X86_64_ACCTON_AS7816_64X_CONFIG_LOG_OPTIONS_DEFAULT:
doc: "Default enabled log options."
default: AIM_LOG_OPTIONS_DEFAULT
- X86_64_ACCTON_AS7816_64X_CONFIG_LOG_BITS_DEFAULT:
doc: "Default enabled log bits."
default: AIM_LOG_BITS_DEFAULT
- X86_64_ACCTON_AS7816_64X_CONFIG_LOG_CUSTOM_BITS_DEFAULT:
doc: "Default enabled custom log bits."
default: 0
- X86_64_ACCTON_AS7816_64X_CONFIG_PORTING_STDLIB:
doc: "Default all porting macros to use the C standard libraries."
default: 1
- X86_64_ACCTON_AS7816_64X_CONFIG_PORTING_INCLUDE_STDLIB_HEADERS:
doc: "Include standard library headers for stdlib porting macros."
default: X86_64_ACCTON_AS7816_64X_CONFIG_PORTING_STDLIB
- X86_64_ACCTON_AS7816_64X_CONFIG_INCLUDE_UCLI:
doc: "Include generic uCli support."
default: 0
- X86_64_ACCTON_AS7816_64X_CONFIG_INCLUDE_DEFAULT_FAN_DIRECTION:
doc: "Assume chassis fan direction is the same as the PSU fan direction."
default: 0
definitions:
cdefs:
X86_64_ACCTON_AS7816_64X_CONFIG_HEADER:
defs: *cdefs
basename: x86_64_accton_as7816_64x_config
portingmacro:
x86_64_accton_as7816_64x:
macros:
- malloc
- free
- memset
- memcpy
- strncpy
- vsnprintf
- snprintf
- strlen

View File

@@ -0,0 +1,14 @@
/**************************************************************************//**
*
*
*
*****************************************************************************/
#include <x86_64_accton_as7816_64x/x86_64_accton_as7816_64x_config.h>
/* <--auto.start.xmacro(ALL).define> */
/* <auto.end.xmacro(ALL).define> */
/* <--auto.start.xenum(ALL).define> */
/* <auto.end.xenum(ALL).define> */

View File

@@ -0,0 +1,137 @@
/**************************************************************************//**
*
* @file
* @brief x86_64_accton_as7816_64x Configuration Header
*
* @addtogroup x86_64_accton_as7816_64x-config
* @{
*
*****************************************************************************/
#ifndef __X86_64_ACCTON_AS7816_64X_CONFIG_H__
#define __X86_64_ACCTON_AS7816_64X_CONFIG_H__
#ifdef GLOBAL_INCLUDE_CUSTOM_CONFIG
#include <global_custom_config.h>
#endif
#ifdef X86_64_ACCTON_AS7816_64X_INCLUDE_CUSTOM_CONFIG
#include <x86_64_accton_as7816_64x_custom_config.h>
#endif
/* <auto.start.cdefs(X86_64_ACCTON_AS7816_64X_CONFIG_HEADER).header> */
#include <AIM/aim.h>
/**
* X86_64_ACCTON_AS7816_64X_CONFIG_INCLUDE_LOGGING
*
* Include or exclude logging. */
#ifndef X86_64_ACCTON_AS7816_64X_CONFIG_INCLUDE_LOGGING
#define X86_64_ACCTON_AS7816_64X_CONFIG_INCLUDE_LOGGING 1
#endif
/**
* X86_64_ACCTON_AS7816_64X_CONFIG_LOG_OPTIONS_DEFAULT
*
* Default enabled log options. */
#ifndef X86_64_ACCTON_AS7816_64X_CONFIG_LOG_OPTIONS_DEFAULT
#define X86_64_ACCTON_AS7816_64X_CONFIG_LOG_OPTIONS_DEFAULT AIM_LOG_OPTIONS_DEFAULT
#endif
/**
* X86_64_ACCTON_AS7816_64X_CONFIG_LOG_BITS_DEFAULT
*
* Default enabled log bits. */
#ifndef X86_64_ACCTON_AS7816_64X_CONFIG_LOG_BITS_DEFAULT
#define X86_64_ACCTON_AS7816_64X_CONFIG_LOG_BITS_DEFAULT AIM_LOG_BITS_DEFAULT
#endif
/**
* X86_64_ACCTON_AS7816_64X_CONFIG_LOG_CUSTOM_BITS_DEFAULT
*
* Default enabled custom log bits. */
#ifndef X86_64_ACCTON_AS7816_64X_CONFIG_LOG_CUSTOM_BITS_DEFAULT
#define X86_64_ACCTON_AS7816_64X_CONFIG_LOG_CUSTOM_BITS_DEFAULT 0
#endif
/**
* X86_64_ACCTON_AS7816_64X_CONFIG_PORTING_STDLIB
*
* Default all porting macros to use the C standard libraries. */
#ifndef X86_64_ACCTON_AS7816_64X_CONFIG_PORTING_STDLIB
#define X86_64_ACCTON_AS7816_64X_CONFIG_PORTING_STDLIB 1
#endif
/**
* X86_64_ACCTON_AS7816_64X_CONFIG_PORTING_INCLUDE_STDLIB_HEADERS
*
* Include standard library headers for stdlib porting macros. */
#ifndef X86_64_ACCTON_AS7816_64X_CONFIG_PORTING_INCLUDE_STDLIB_HEADERS
#define X86_64_ACCTON_AS7816_64X_CONFIG_PORTING_INCLUDE_STDLIB_HEADERS X86_64_ACCTON_AS7816_64X_CONFIG_PORTING_STDLIB
#endif
/**
* X86_64_ACCTON_AS7816_64X_CONFIG_INCLUDE_UCLI
*
* Include generic uCli support. */
#ifndef X86_64_ACCTON_AS7816_64X_CONFIG_INCLUDE_UCLI
#define X86_64_ACCTON_AS7816_64X_CONFIG_INCLUDE_UCLI 0
#endif
/**
* X86_64_ACCTON_AS7816_64X_CONFIG_INCLUDE_DEFAULT_FAN_DIRECTION
*
* Assume chassis fan direction is the same as the PSU fan direction. */
#ifndef X86_64_ACCTON_AS7816_64X_CONFIG_INCLUDE_DEFAULT_FAN_DIRECTION
#define X86_64_ACCTON_AS7816_64X_CONFIG_INCLUDE_DEFAULT_FAN_DIRECTION 0
#endif
/**
* All compile time options can be queried or displayed
*/
/** Configuration settings structure. */
typedef struct x86_64_accton_as7816_64x_config_settings_s {
/** name */
const char* name;
/** value */
const char* value;
} x86_64_accton_as7816_64x_config_settings_t;
/** Configuration settings table. */
/** x86_64_accton_as7816_64x_config_settings table. */
extern x86_64_accton_as7816_64x_config_settings_t x86_64_accton_as7816_64x_config_settings[];
/**
* @brief Lookup a configuration setting.
* @param setting The name of the configuration option to lookup.
*/
const char* x86_64_accton_as7816_64x_config_lookup(const char* setting);
/**
* @brief Show the compile-time configuration.
* @param pvs The output stream.
*/
int x86_64_accton_as7816_64x_config_show(struct aim_pvs_s* pvs);
/* <auto.end.cdefs(X86_64_ACCTON_AS7816_64X_CONFIG_HEADER).header> */
#include "x86_64_accton_as7816_64x_porting.h"
#endif /* __X86_64_ACCTON_AS7816_64X_CONFIG_H__ */
/* @} */

View File

@@ -0,0 +1,26 @@
/**************************************************************************//**
*
* x86_64_accton_as7816_64x Doxygen Header
*
*****************************************************************************/
#ifndef __X86_64_ACCTON_AS7816_64X_DOX_H__
#define __X86_64_ACCTON_AS7816_64X_DOX_H__
/**
* @defgroup x86_64_accton_as7816_64x x86_64_accton_as7816_64x - x86_64_accton_as7816_64x Description
*
The documentation overview for this module should go here.
*
* @{
*
* @defgroup x86_64_accton_as7816_64x-x86_64_accton_as7816_64x Public Interface
* @defgroup x86_64_accton_as7816_64x-config Compile Time Configuration
* @defgroup x86_64_accton_as7816_64x-porting Porting Macros
*
* @}
*
*/
#endif /* __X86_64_ACCTON_AS7816_64X_DOX_H__ */

View File

@@ -0,0 +1,107 @@
/**************************************************************************//**
*
* @file
* @brief x86_64_accton_as7816_64x Porting Macros.
*
* @addtogroup x86_64_accton_as7816_64x-porting
* @{
*
*****************************************************************************/
#ifndef __X86_64_ACCTON_AS7816_64X_PORTING_H__
#define __X86_64_ACCTON_AS7816_64X_PORTING_H__
/* <auto.start.portingmacro(ALL).define> */
#if X86_64_ACCTON_AS7816_64X_CONFIG_PORTING_INCLUDE_STDLIB_HEADERS == 1
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <stdarg.h>
#include <memory.h>
#endif
#ifndef x86_64_accton_as7816_64x_MALLOC
#if defined(GLOBAL_MALLOC)
#define x86_64_accton_as7816_64x_MALLOC GLOBAL_MALLOC
#elif X86_64_ACCTON_AS7816_64X_CONFIG_PORTING_STDLIB == 1
#define x86_64_accton_as7816_64x_MALLOC malloc
#else
#error The macro x86_64_accton_as7816_64x_MALLOC is required but cannot be defined.
#endif
#endif
#ifndef x86_64_accton_as7816_64x_FREE
#if defined(GLOBAL_FREE)
#define x86_64_accton_as7816_64x_FREE GLOBAL_FREE
#elif X86_64_ACCTON_AS7816_64X_CONFIG_PORTING_STDLIB == 1
#define x86_64_accton_as7816_64x_FREE free
#else
#error The macro x86_64_accton_as7816_64x_FREE is required but cannot be defined.
#endif
#endif
#ifndef x86_64_accton_as7816_64x_MEMSET
#if defined(GLOBAL_MEMSET)
#define x86_64_accton_as7816_64x_MEMSET GLOBAL_MEMSET
#elif X86_64_ACCTON_AS7816_64X_CONFIG_PORTING_STDLIB == 1
#define x86_64_accton_as7816_64x_MEMSET memset
#else
#error The macro x86_64_accton_as7816_64x_MEMSET is required but cannot be defined.
#endif
#endif
#ifndef x86_64_accton_as7816_64x_MEMCPY
#if defined(GLOBAL_MEMCPY)
#define x86_64_accton_as7816_64x_MEMCPY GLOBAL_MEMCPY
#elif X86_64_ACCTON_AS7816_64X_CONFIG_PORTING_STDLIB == 1
#define x86_64_accton_as7816_64x_MEMCPY memcpy
#else
#error The macro x86_64_accton_as7816_64x_MEMCPY is required but cannot be defined.
#endif
#endif
#ifndef x86_64_accton_as7816_64x_STRNCPY
#if defined(GLOBAL_STRNCPY)
#define x86_64_accton_as7816_64x_STRNCPY GLOBAL_STRNCPY
#elif X86_64_ACCTON_AS7816_64X_CONFIG_PORTING_STDLIB == 1
#define x86_64_accton_as7816_64x_STRNCPY strncpy
#else
#error The macro x86_64_accton_as7816_64x_STRNCPY is required but cannot be defined.
#endif
#endif
#ifndef x86_64_accton_as7816_64x_VSNPRINTF
#if defined(GLOBAL_VSNPRINTF)
#define x86_64_accton_as7816_64x_VSNPRINTF GLOBAL_VSNPRINTF
#elif X86_64_ACCTON_AS7816_64X_CONFIG_PORTING_STDLIB == 1
#define x86_64_accton_as7816_64x_VSNPRINTF vsnprintf
#else
#error The macro x86_64_accton_as7816_64x_VSNPRINTF is required but cannot be defined.
#endif
#endif
#ifndef x86_64_accton_as7816_64x_SNPRINTF
#if defined(GLOBAL_SNPRINTF)
#define x86_64_accton_as7816_64x_SNPRINTF GLOBAL_SNPRINTF
#elif X86_64_ACCTON_AS7816_64X_CONFIG_PORTING_STDLIB == 1
#define x86_64_accton_as7816_64x_SNPRINTF snprintf
#else
#error The macro x86_64_accton_as7816_64x_SNPRINTF is required but cannot be defined.
#endif
#endif
#ifndef x86_64_accton_as7816_64x_STRLEN
#if defined(GLOBAL_STRLEN)
#define x86_64_accton_as7816_64x_STRLEN GLOBAL_STRLEN
#elif X86_64_ACCTON_AS7816_64X_CONFIG_PORTING_STDLIB == 1
#define x86_64_accton_as7816_64x_STRLEN strlen
#else
#error The macro x86_64_accton_as7816_64x_STRLEN is required but cannot be defined.
#endif
#endif
/* <auto.end.portingmacro(ALL).define> */
#endif /* __X86_64_ACCTON_AS7816_64X_PORTING_H__ */
/* @} */

View File

@@ -0,0 +1,10 @@
###############################################################################
#
#
#
###############################################################################
THIS_DIR := $(dir $(lastword $(MAKEFILE_LIST)))
x86_64_accton_as7816_64x_INCLUDES := -I $(THIS_DIR)inc
x86_64_accton_as7816_64x_INTERNAL_INCLUDES := -I $(THIS_DIR)src
x86_64_accton_as7816_64x_DEPENDMODULE_ENTRIES := init:x86_64_accton_as7816_64x ucli:x86_64_accton_as7816_64x

View File

@@ -0,0 +1,9 @@
###############################################################################
#
# Local source generation targets.
#
###############################################################################
ucli:
@../../../../tools/uclihandlers.py x86_64_accton_as7816_64x_ucli.c

View File

@@ -0,0 +1,280 @@
/************************************************************
* <bsn.cl fy=2014 v=onl>
*
* Copyright 2014 Big Switch Networks, Inc.
* Copyright 2017 Accton Technology Corporation.
*
* Licensed under the Eclipse Public License, Version 1.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.eclipse.org/legal/epl-v10.html
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND,
* either express or implied. See the License for the specific
* language governing permissions and limitations under the
* License.
*
* </bsn.cl>
************************************************************
*
* Fan Platform Implementation Defaults.
*
***********************************************************/
#include <onlplib/file.h>
#include <onlp/platformi/fani.h>
#include "platform_lib.h"
enum fan_id {
FAN_1_ON_FAN_BOARD = 1,
FAN_2_ON_FAN_BOARD,
FAN_3_ON_FAN_BOARD,
FAN_4_ON_FAN_BOARD,
FAN_1_ON_PSU_1,
FAN_1_ON_PSU_2
};
#define MAX_FAN_SPEED 25500
#define MAX_PSU_FAN_SPEED 18000
#define CHASSIS_FAN_INFO(fid) \
{ \
{ ONLP_FAN_ID_CREATE(FAN_##fid##_ON_FAN_BOARD), "Chassis Fan - "#fid, 0 },\
0x0,\
ONLP_FAN_CAPS_SET_PERCENTAGE | ONLP_FAN_CAPS_GET_RPM | ONLP_FAN_CAPS_GET_PERCENTAGE,\
0,\
0,\
ONLP_FAN_MODE_INVALID,\
}
#define PSU_FAN_INFO(pid, fid) \
{ \
{ ONLP_FAN_ID_CREATE(FAN_##fid##_ON_PSU_##pid), "PSU "#pid" - Fan "#fid, 0 },\
0x0,\
ONLP_FAN_CAPS_GET_RPM | ONLP_FAN_CAPS_GET_PERCENTAGE,\
0,\
0,\
ONLP_FAN_MODE_INVALID,\
}
/* Static fan information */
onlp_fan_info_t finfo[] = {
{ }, /* Not used */
CHASSIS_FAN_INFO(1),
CHASSIS_FAN_INFO(2),
CHASSIS_FAN_INFO(3),
CHASSIS_FAN_INFO(4),
PSU_FAN_INFO(1, 1),
PSU_FAN_INFO(2, 1)
};
#define VALIDATE(_id) \
do { \
if(!ONLP_OID_IS_FAN(_id)) { \
return ONLP_STATUS_E_INVALID; \
} \
} while(0)
static int
_onlp_fani_info_get_fan(int fid, onlp_fan_info_t* info)
{
int value;
/* get fan present status
*/
if (onlp_file_read_int(&value, "%s""fan%d_present", FAN_BOARD_PATH, fid) < 0) {
AIM_LOG_ERROR("Unable to read status from (%s)\r\n", FAN_BOARD_PATH);
return ONLP_STATUS_E_INTERNAL;
}
if (value == 0) {
return ONLP_STATUS_OK; /* fan is not present */
}
info->status |= ONLP_FAN_STATUS_PRESENT;
/* get fan fault status (turn on when any one fails)
*/
if (onlp_file_read_int(&value, "%s""fan%d_fault", FAN_BOARD_PATH, fid) < 0) {
AIM_LOG_ERROR("Unable to read status from (%s)\r\n", FAN_BOARD_PATH);
return ONLP_STATUS_E_INTERNAL;
}
if (value > 0) {
info->status |= ONLP_FAN_STATUS_FAILED;
}
/* get fan direction (both : the same)
*/
if (onlp_file_read_int(&value, "%s""fan%d_direction", FAN_BOARD_PATH, fid) < 0) {
AIM_LOG_ERROR("Unable to read status from (%s)\r\n", FAN_BOARD_PATH);
return ONLP_STATUS_E_INTERNAL;
}
info->status |= value ? ONLP_FAN_STATUS_B2F : ONLP_FAN_STATUS_F2B;
/* get front fan speed
*/
if (onlp_file_read_int(&value, "%s""fan%d_front_speed_rpm", FAN_BOARD_PATH, fid) < 0) {
AIM_LOG_ERROR("Unable to read status from (%s)\r\n", FAN_BOARD_PATH);
return ONLP_STATUS_E_INTERNAL;
}
info->rpm = value;
/* get rear fan speed
*/
if (onlp_file_read_int(&value, "%s""fan%d_rear_speed_rpm", FAN_BOARD_PATH, fid) < 0) {
AIM_LOG_ERROR("Unable to read status from (%s)\r\n", FAN_BOARD_PATH);
return ONLP_STATUS_E_INTERNAL;
}
/* take the min value from front/rear fan speed
*/
if (info->rpm > value) {
info->rpm = value;
}
/* get speed percentage from rpm
*/
info->percentage = (info->rpm * 100)/MAX_FAN_SPEED;
return ONLP_STATUS_OK;
}
static uint32_t
_onlp_get_fan_direction_on_psu(void)
{
/* Try to read direction from PSU1.
* If PSU1 is not valid, read from PSU2
*/
int i = 0;
for (i = PSU1_ID; i <= PSU2_ID; i++) {
psu_type_t psu_type;
psu_type = psu_type_get(i, NULL, 0);
if (psu_type == PSU_TYPE_UNKNOWN) {
continue;
}
switch (psu_type) {
case PSU_TYPE_AC_YM2851_F2B:
return ONLP_FAN_STATUS_F2B;
case PSU_TYPE_AC_YM2851_B2F:
return ONLP_FAN_STATUS_B2F;
default:
return 0;
};
}
return 0;
}
static int
_onlp_fani_info_get_fan_on_psu(int pid, onlp_fan_info_t* info)
{
int val = 0;
info->status |= ONLP_FAN_STATUS_PRESENT;
/* get fan direction
*/
info->status |= _onlp_get_fan_direction_on_psu();
/* get fan speed
*/
if (psu_ym2651y_pmbus_info_get(pid, "psu_fan1_speed_rpm", &val) == ONLP_STATUS_OK) {
info->rpm = val;
info->percentage = (info->rpm * 100) / MAX_PSU_FAN_SPEED;
info->status |= (val == 0) ? ONLP_FAN_STATUS_FAILED : 0;
}
return ONLP_STATUS_OK;
}
/*
* This function will be called prior to all of onlp_fani_* functions.
*/
int
onlp_fani_init(void)
{
return ONLP_STATUS_OK;
}
int
onlp_fani_info_get(onlp_oid_t id, onlp_fan_info_t* info)
{
int rc = 0;
int fid;
VALIDATE(id);
fid = ONLP_OID_ID_GET(id);
*info = finfo[fid];
switch (fid)
{
case FAN_1_ON_PSU_1:
rc = _onlp_fani_info_get_fan_on_psu(PSU1_ID, info);
break;
case FAN_1_ON_PSU_2:
rc = _onlp_fani_info_get_fan_on_psu(PSU2_ID, info);
break;
case FAN_1_ON_FAN_BOARD:
case FAN_2_ON_FAN_BOARD:
case FAN_3_ON_FAN_BOARD:
case FAN_4_ON_FAN_BOARD:
rc =_onlp_fani_info_get_fan(fid, info);
break;
default:
rc = ONLP_STATUS_E_INVALID;
break;
}
return rc;
}
/*
* This function sets the fan speed of the given OID as a percentage.
*
* This will only be called if the OID has the PERCENTAGE_SET
* capability.
*
* It is optional if you have no fans at all with this feature.
*/
int
onlp_fani_percentage_set(onlp_oid_t id, int p)
{
int fid;
char *path = NULL;
VALIDATE(id);
fid = ONLP_OID_ID_GET(id);
/* reject p=0 (p=0, stop fan) */
if (p == 0){
return ONLP_STATUS_E_INVALID;
}
switch (fid)
{
case FAN_1_ON_FAN_BOARD:
case FAN_2_ON_FAN_BOARD:
path = FAN_NODE(fan_duty_cycle_percentage);
break;
default:
return ONLP_STATUS_E_INVALID;
}
if (onlp_file_write_int(p, path) < 0) {
AIM_LOG_ERROR("Unable to write data to file (%s)\r\n", path);
return ONLP_STATUS_E_INTERNAL;
}
return ONLP_STATUS_OK;
}

View File

@@ -0,0 +1,241 @@
/************************************************************
* <bsn.cl fy=2014 v=onl>
*
* Copyright 2014 Big Switch Networks, Inc.
* Copyright 2017 Accton Technology Corporation.
*
* Licensed under the Eclipse Public License, Version 1.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.eclipse.org/legal/epl-v10.html
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND,
* either express or implied. See the License for the specific
* language governing permissions and limitations under the
* License.
*
* </bsn.cl>
************************************************************
*
*
*
***********************************************************/
#include <onlplib/file.h>
#include <onlp/platformi/ledi.h>
#include "platform_lib.h"
#define LED_FORMAT "/sys/class/leds/as7816_64x_led::%s/brightness"
#define VALIDATE(_id) \
do { \
if(!ONLP_OID_IS_LED(_id)) { \
return ONLP_STATUS_E_INVALID; \
} \
} while(0)
/* LED related data
*/
enum led_light_mode {
LED_MODE_OFF,
LED_MODE_RED = 10,
LED_MODE_RED_BLINKING = 11,
LED_MODE_ORANGE = 12,
LED_MODE_ORANGE_BLINKING = 13,
LED_MODE_YELLOW = 14,
LED_MODE_YELLOW_BLINKING = 15,
LED_MODE_GREEN = 16,
LED_MODE_GREEN_BLINKING = 17,
LED_MODE_BLUE = 18,
LED_MODE_BLUE_BLINKING = 19,
LED_MODE_PURPLE = 20,
LED_MODE_PURPLE_BLINKING = 21,
LED_MODE_AUTO = 22,
LED_MODE_AUTO_BLINKING = 23,
LED_MODE_WHITE = 24,
LED_MODE_WHITE_BLINKING = 25,
LED_MODE_CYAN = 26,
LED_MODE_CYAN_BLINKING = 27,
LED_MODE_UNKNOWN = 99
};
typedef struct led_light_mode_map {
enum onlp_led_id id;
enum led_light_mode driver_led_mode;
enum onlp_led_mode_e onlp_led_mode;
} led_light_mode_map_t;
led_light_mode_map_t led_map[] = {
{LED_DIAG, LED_MODE_OFF, ONLP_LED_MODE_OFF},
{LED_DIAG, LED_MODE_GREEN, ONLP_LED_MODE_GREEN},
{LED_DIAG, LED_MODE_RED, ONLP_LED_MODE_RED},
{LED_DIAG, LED_MODE_YELLOW,ONLP_LED_MODE_YELLOW},
{LED_LOC, LED_MODE_OFF, ONLP_LED_MODE_OFF},
{LED_LOC, LED_MODE_ORANGE,ONLP_LED_MODE_ORANGE},
{LED_FAN, LED_MODE_OFF, ONLP_LED_MODE_OFF},
{LED_FAN, LED_MODE_GREEN, ONLP_LED_MODE_GREEN},
{LED_FAN, LED_MODE_ORANGE,ONLP_LED_MODE_ORANGE},
{LED_PSU1, LED_MODE_AUTO, ONLP_LED_MODE_AUTO},
{LED_PSU2, LED_MODE_AUTO, ONLP_LED_MODE_AUTO}
};
static char *leds[] = /* must map with onlp_led_id */
{
"reserved",
"psu1",
"psu2",
"fan",
"diag",
"loc",
};
/*
* Get the information for the given LED OID.
*/
static onlp_led_info_t linfo[] =
{
{ }, /* Not used */
{
{ ONLP_LED_ID_CREATE(LED_PSU1), "Chassis LED 1 (PSU1 LED)", 0 },
ONLP_LED_STATUS_PRESENT,
ONLP_LED_CAPS_AUTO,
},
{
{ ONLP_LED_ID_CREATE(LED_PSU1), "Chassis LED 2 (PSU2 LED)", 0 },
ONLP_LED_STATUS_PRESENT,
ONLP_LED_CAPS_AUTO,
},
{
{ ONLP_LED_ID_CREATE(LED_FAN), "Chassis LED 3 (FAN LED)", 0 },
ONLP_LED_STATUS_PRESENT,
ONLP_LED_CAPS_ON_OFF | ONLP_LED_CAPS_GREEN | ONLP_LED_CAPS_ORANGE,
},
{
{ ONLP_LED_ID_CREATE(LED_DIAG), "Chassis LED 4 (DIAG LED)", 0 },
ONLP_LED_STATUS_PRESENT,
ONLP_LED_CAPS_ON_OFF | ONLP_LED_CAPS_GREEN | ONLP_LED_CAPS_RED | ONLP_LED_CAPS_YELLOW,
},
{
{ ONLP_LED_ID_CREATE(LED_LOC), "Chassis LED 5 (LOC LED)", 0 },
ONLP_LED_STATUS_PRESENT,
ONLP_LED_CAPS_ON_OFF | ONLP_LED_CAPS_RED,
},
};
static int driver_to_onlp_led_mode(enum onlp_led_id id, enum led_light_mode driver_led_mode)
{
int i, nsize = sizeof(led_map)/sizeof(led_map[0]);
for (i = 0; i < nsize; i++)
{
if (id == led_map[i].id && driver_led_mode == led_map[i].driver_led_mode)
{
return led_map[i].onlp_led_mode;
}
}
return 0;
}
static int onlp_to_driver_led_mode(enum onlp_led_id id, onlp_led_mode_t onlp_led_mode)
{
int i, nsize = sizeof(led_map)/sizeof(led_map[0]);
for(i = 0; i < nsize; i++)
{
if (id == led_map[i].id && onlp_led_mode == led_map[i].onlp_led_mode)
{
return led_map[i].driver_led_mode;
}
}
return 0;
}
/*
* This function will be called prior to any other onlp_ledi_* functions.
*/
int
onlp_ledi_init(void)
{
/*
* LED Off
*/
onlp_ledi_mode_set(ONLP_LED_ID_CREATE(LED_DIAG), ONLP_LED_MODE_OFF);
onlp_ledi_mode_set(ONLP_LED_ID_CREATE(LED_LOC), ONLP_LED_MODE_OFF);
return ONLP_STATUS_OK;
}
int
onlp_ledi_info_get(onlp_oid_t id, onlp_led_info_t* info)
{
int lid, value;
VALIDATE(id);
lid = ONLP_OID_ID_GET(id);
/* Set the onlp_oid_hdr_t and capabilities */
*info = linfo[ONLP_OID_ID_GET(id)];
/* Get LED mode */
if (onlp_file_read_int(&value, LED_FORMAT, leds[lid]) < 0) {
DEBUG_PRINT("Unable to read status from file "LED_FORMAT, leds[lid]);
return ONLP_STATUS_E_INTERNAL;
}
info->mode = driver_to_onlp_led_mode(lid, value);
/* Set the on/off status */
if (info->mode != ONLP_LED_MODE_OFF) {
info->status |= ONLP_LED_STATUS_ON;
}
return ONLP_STATUS_OK;
}
/*
* Turn an LED on or off.
*
* This function will only be called if the LED OID supports the ONOFF
* capability.
*
* What 'on' means in terms of colors or modes for multimode LEDs is
* up to the platform to decide. This is intended as baseline toggle mechanism.
*/
int
onlp_ledi_set(onlp_oid_t id, int on_or_off)
{
VALIDATE(id);
if (!on_or_off) {
return onlp_ledi_mode_set(id, ONLP_LED_MODE_OFF);
}
return ONLP_STATUS_E_UNSUPPORTED;
}
/*
* This function puts the LED into the given mode. It is a more functional
* interface for multimode LEDs.
*
* Only modes reported in the LED's capabilities will be attempted.
*/
int
onlp_ledi_mode_set(onlp_oid_t id, onlp_led_mode_t mode)
{
int lid;
VALIDATE(id);
lid = ONLP_OID_ID_GET(id);
if (onlp_file_write_int(onlp_to_driver_led_mode(lid , mode), LED_FORMAT, leds[lid]) < 0) {
return ONLP_STATUS_E_INTERNAL;
}
return ONLP_STATUS_OK;
}

View File

@@ -0,0 +1,9 @@
###############################################################################
#
#
#
###############################################################################
LIBRARY := x86_64_accton_as7816_64x
$(LIBRARY)_SUBDIR := $(dir $(lastword $(MAKEFILE_LIST)))
include $(BUILDER)/lib.mk

View File

@@ -0,0 +1,126 @@
/************************************************************
* <bsn.cl fy=2014 v=onl>
*
* Copyright 2014 Big Switch Networks, Inc.
* Copyright 2014 Accton Technology Corporation.
*
* Licensed under the Eclipse Public License, Version 1.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.eclipse.org/legal/epl-v10.html
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND,
* either express or implied. See the License for the specific
* language governing permissions and limitations under the
* License.
*
* </bsn.cl>
************************************************************
*
*
*
***********************************************************/
#include <onlp/onlp.h>
#include <onlplib/file.h>
#include <onlplib/i2c.h>
#include <AIM/aim.h>
#include "platform_lib.h"
#define PSU_MODEL_NAME_LEN 8
#define PSU_SERIAL_NUMBER_LEN 14
#define PSU_NODE_MAX_PATH_LEN 64
int psu_serial_number_get(int id, char *serial, int serial_len)
{
int size = 0;
int ret = ONLP_STATUS_OK;
char *prefix = NULL;
if (serial == NULL || serial_len < PSU_SERIAL_NUMBER_LEN) {
return ONLP_STATUS_E_PARAM;
}
prefix = (id == PSU1_ID) ? PSU1_AC_PMBUS_PREFIX : PSU2_AC_PMBUS_PREFIX;
ret = onlp_file_read((uint8_t*)serial, PSU_SERIAL_NUMBER_LEN, &size, "%s%s", prefix, "psu_mfr_serial");
if (ret != ONLP_STATUS_OK || size != PSU_SERIAL_NUMBER_LEN) {
return ONLP_STATUS_E_INTERNAL;
}
serial[PSU_SERIAL_NUMBER_LEN] = '\0';
return ONLP_STATUS_OK;
}
psu_type_t psu_type_get(int id, char* modelname, int modelname_len)
{
int value = 0;
int ret = ONLP_STATUS_OK;
char model[PSU_MODEL_NAME_LEN + 1] = {0};
char *prefix = NULL;
if (modelname && modelname_len < PSU_MODEL_NAME_LEN) {
return PSU_TYPE_UNKNOWN;
}
/* Check if the psu is power good
*/
prefix = (id == PSU1_ID) ? PSU1_AC_EEPROM_PREFIX : PSU2_AC_EEPROM_PREFIX;
if (onlp_file_read_int(&value, "%s%s", prefix, "psu_power_good") < 0) {
AIM_LOG_ERROR("Unable to read status from file(%s%s)\r\n", prefix, "psu_power_good");
return ONLP_STATUS_E_INTERNAL;
}
if (!value) {
return PSU_TYPE_UNKNOWN;
}
/* Read mode name */
prefix = (id == PSU1_ID) ? PSU1_AC_PMBUS_PREFIX : PSU2_AC_PMBUS_PREFIX;
ret = onlp_file_read((uint8_t*)model, PSU_MODEL_NAME_LEN, &value, "%s%s", prefix, "psu_mfr_model");
if (ret != ONLP_STATUS_OK || value != PSU_MODEL_NAME_LEN) {
return PSU_TYPE_UNKNOWN;
}
if (modelname) {
memcpy(modelname, model, sizeof(model));
}
if (strncmp(model, "YM-2851F", strlen("YM-2851F")) == 0) {
return PSU_TYPE_AC_YM2851_F2B;
}
return PSU_TYPE_UNKNOWN;
}
int psu_ym2651y_pmbus_info_get(int id, char *node, int *value)
{
char *prefix = NULL;
*value = 0;
prefix = (id == PSU1_ID) ? PSU1_AC_PMBUS_PREFIX : PSU2_AC_PMBUS_PREFIX;
if (onlp_file_read_int(value, "%s%s", prefix, node) < 0) {
AIM_LOG_ERROR("Unable to read status from file(%s%s)\r\n", prefix, node);
return ONLP_STATUS_E_INTERNAL;
}
return ONLP_STATUS_OK;
}
int psu_ym2651y_pmbus_info_set(int id, char *node, int value)
{
char *prefix = NULL;
prefix = (id == PSU1_ID) ? PSU1_AC_PMBUS_PREFIX : PSU2_AC_PMBUS_PREFIX;
if (onlp_file_write_int(value, "%s%s", prefix, node) < 0) {
AIM_LOG_ERROR("Unable to write data to file (%s%s)\r\n", prefix, node);
return ONLP_STATUS_E_INTERNAL;
}
return ONLP_STATUS_OK;
}

View File

@@ -0,0 +1,101 @@
/************************************************************
* <bsn.cl fy=2014 v=onl>
*
* Copyright 2014 Big Switch Networks, Inc.
* Copyright 2014 Accton Technology Corporation.
*
* Licensed under the Eclipse Public License, Version 1.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.eclipse.org/legal/epl-v10.html
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND,
* either express or implied. See the License for the specific
* language governing permissions and limitations under the
* License.
*
* </bsn.cl>
************************************************************
*
*
*
***********************************************************/
#ifndef __PLATFORM_LIB_H__
#define __PLATFORM_LIB_H__
#include "x86_64_accton_as7816_64x_log.h"
#define CHASSIS_FAN_COUNT 4
#define CHASSIS_THERMAL_COUNT 7
#define CHASSIS_LED_COUNT 5
#define CHASSIS_PSU_COUNT 2
#define PSU1_ID 1
#define PSU2_ID 2
#define PSU1_AC_PMBUS_PREFIX "/sys/bus/i2c/devices/10-005b/"
#define PSU2_AC_PMBUS_PREFIX "/sys/bus/i2c/devices/9-0058/"
#define PSU1_AC_PMBUS_NODE(node) PSU1_AC_PMBUS_PREFIX#node
#define PSU2_AC_PMBUS_NODE(node) PSU2_AC_PMBUS_PREFIX#node
#define PSU1_AC_EEPROM_PREFIX "/sys/bus/i2c/devices/10-0053/"
#define PSU2_AC_EEPROM_PREFIX "/sys/bus/i2c/devices/9-0050/"
#define PSU1_AC_EEPROM_NODE(node) PSU1_AC_EEPROM_PREFIX#node
#define PSU2_AC_EEPROM_NODE(node) PSU2_AC_EEPROM_PREFIX#node
#define FAN_BOARD_PATH "/sys/bus/i2c/devices/17-0068/"
#define FAN_NODE(node) FAN_BOARD_PATH#node
#define IDPROM_PATH "/sys/bus/i2c/devices/0-0056/eeprom"
enum onlp_led_id
{
LED_RESERVED = 0,
LED_PSU1,
LED_PSU2,
LED_FAN,
LED_DIAG,
LED_LOC
};
enum onlp_thermal_id
{
THERMAL_RESERVED = 0,
THERMAL_CPU_CORE,
THERMAL_1_ON_MAIN_BROAD,
THERMAL_2_ON_MAIN_BROAD,
THERMAL_3_ON_MAIN_BROAD,
THERMAL_4_ON_MAIN_BROAD,
THERMAL_5_ON_MAIN_BROAD,
THERMAL_6_ON_MAIN_BROAD,
THERMAL_1_ON_PSU1,
THERMAL_1_ON_PSU2,
};
typedef enum psu_type {
PSU_TYPE_UNKNOWN,
PSU_TYPE_AC_YM2851_F2B,
PSU_TYPE_AC_YM2851_B2F
} psu_type_t;
psu_type_t psu_type_get(int id, char* modelname, int modelname_len);
int psu_serial_number_get(int id, char *serial, int serial_len);
int psu_ym2651y_pmbus_info_get(int id, char *node, int *value);
int psu_ym2651y_pmbus_info_set(int id, char *node, int value);
#define DEBUG_MODE 0
#if (DEBUG_MODE == 1)
#define DEBUG_PRINT(fmt, args...) \
printf("%s:%s[%d]: " fmt "\r\n", __FILE__, __FUNCTION__, __LINE__, ##args)
#else
#define DEBUG_PRINT(fmt, args...)
#endif
#endif /* __PLATFORM_LIB_H__ */

View File

@@ -0,0 +1,170 @@
/************************************************************
* <bsn.cl fy=2014 v=onl>
*
* Copyright 2014 Big Switch Networks, Inc.
* Copyright 2014 Accton Technology Corporation.
*
* Licensed under the Eclipse Public License, Version 1.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.eclipse.org/legal/epl-v10.html
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND,
* either express or implied. See the License for the specific
* language governing permissions and limitations under the
* License.
*
* </bsn.cl>
************************************************************
*
*
*
***********************************************************/
#include <onlp/platformi/psui.h>
#include <onlplib/file.h>
#include "platform_lib.h"
#define PSU_STATUS_PRESENT 1
#define PSU_STATUS_POWER_GOOD 1
#define VALIDATE(_id) \
do { \
if(!ONLP_OID_IS_PSU(_id)) { \
return ONLP_STATUS_E_INVALID; \
} \
} while(0)
static int
psu_status_info_get(int id, char *node, int *value)
{
char *prefix = NULL;
*value = 0;
prefix = (id == PSU1_ID) ? PSU1_AC_EEPROM_PREFIX : PSU2_AC_EEPROM_PREFIX;
if (onlp_file_read_int(value, "%s%s", prefix, node) < 0) {
AIM_LOG_ERROR("Unable to read status from file(%s%s)\r\n", prefix, node);
return ONLP_STATUS_E_INTERNAL;
}
return 0;
}
int
onlp_psui_init(void)
{
return ONLP_STATUS_OK;
}
static int
psu_ym2651y_info_get(onlp_psu_info_t* info)
{
int val = 0;
int index = ONLP_OID_ID_GET(info->hdr.id);
/* Set capability
*/
info->caps = ONLP_PSU_CAPS_AC;
if (info->status & ONLP_PSU_STATUS_FAILED) {
return ONLP_STATUS_OK;
}
/* Set the associated oid_table */
info->hdr.coids[0] = ONLP_FAN_ID_CREATE(index + CHASSIS_FAN_COUNT);
info->hdr.coids[1] = ONLP_THERMAL_ID_CREATE(index + CHASSIS_THERMAL_COUNT);
/* Read voltage, current and power */
if (psu_ym2651y_pmbus_info_get(index, "psu_v_out", &val) == 0) {
info->mvout = val;
info->caps |= ONLP_PSU_CAPS_VOUT;
}
if (psu_ym2651y_pmbus_info_get(index, "psu_i_out", &val) == 0) {
info->miout = val;
info->caps |= ONLP_PSU_CAPS_IOUT;
}
if (psu_ym2651y_pmbus_info_get(index, "psu_p_out", &val) == 0) {
info->mpout = val;
info->caps |= ONLP_PSU_CAPS_POUT;
}
psu_serial_number_get(index, info->serial, sizeof(info->serial));
return ONLP_STATUS_OK;
}
/*
* Get all information about the given PSU oid.
*/
static onlp_psu_info_t pinfo[] =
{
{ }, /* Not used */
{
{ ONLP_PSU_ID_CREATE(PSU1_ID), "PSU-1", 0 },
},
{
{ ONLP_PSU_ID_CREATE(PSU2_ID), "PSU-2", 0 },
}
};
int
onlp_psui_info_get(onlp_oid_t id, onlp_psu_info_t* info)
{
int val = 0;
int ret = ONLP_STATUS_OK;
int index = ONLP_OID_ID_GET(id);
psu_type_t psu_type;
VALIDATE(id);
memset(info, 0, sizeof(onlp_psu_info_t));
*info = pinfo[index]; /* Set the onlp_oid_hdr_t */
/* Get the present state */
if (psu_status_info_get(index, "psu_present", &val) != 0) {
printf("Unable to read PSU(%d) node(psu_present)\r\n", index);
}
if (val != PSU_STATUS_PRESENT) {
info->status &= ~ONLP_PSU_STATUS_PRESENT;
return ONLP_STATUS_OK;
}
info->status |= ONLP_PSU_STATUS_PRESENT;
/* Get power good status */
if (psu_status_info_get(index, "psu_power_good", &val) != 0) {
printf("Unable to read PSU(%d) node(psu_power_good)\r\n", index);
}
if (val != PSU_STATUS_POWER_GOOD) {
info->status |= ONLP_PSU_STATUS_FAILED;
}
/* Get PSU type
*/
psu_type = psu_type_get(index, info->model, sizeof(info->model));
switch (psu_type) {
case PSU_TYPE_AC_YM2851_F2B:
case PSU_TYPE_AC_YM2851_B2F:
ret = psu_ym2651y_info_get(info);
break;
case PSU_TYPE_UNKNOWN: /* User insert a unknown PSU or unplugged.*/
info->status |= ONLP_PSU_STATUS_UNPLUGGED;
info->status &= ~ONLP_PSU_STATUS_FAILED;
ret = ONLP_STATUS_OK;
break;
default:
ret = ONLP_STATUS_E_UNSUPPORTED;
break;
}
return ret;
}

View File

@@ -0,0 +1,179 @@
/************************************************************
* <bsn.cl fy=2014 v=onl>
*
* Copyright 2014 Big Switch Networks, Inc.
* Copyright 2017 Accton Technology Corporation.
*
* Licensed under the Eclipse Public License, Version 1.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.eclipse.org/legal/epl-v10.html
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND,
* either express or implied. See the License for the specific
* language governing permissions and limitations under the
* License.
*
* </bsn.cl>
************************************************************
*
*
*
***********************************************************/
#include <onlp/platformi/sfpi.h>
#include <onlplib/i2c.h>
#include <onlplib/file.h>
#include "platform_lib.h"
#define NUM_OF_SFP_PORT 64
static const int port_bus_index[NUM_OF_SFP_PORT] = {
37, 38, 39, 40, 42, 41, 44, 43,
33, 34, 35, 36, 45, 46, 47, 48,
49, 50, 51, 52, 61, 62, 63, 64,
53, 54, 55, 56, 57, 58, 59, 60,
69, 70, 71, 72, 77, 78, 79, 80,
65, 66, 67, 68, 73, 74, 75, 76,
85, 86, 87, 88, 31, 32, 29, 30,
81, 82, 83, 84, 25, 26, 27, 28
};
#define QSFP_BUS_INDEX(port) (port_bus_index[port])
#define QSFP_PORT_FORMAT "/sys/bus/i2c/devices/%d-0050/%s"
/************************************************************
*
* SFPI Entry Points
*
***********************************************************/
int
onlp_sfpi_init(void)
{
/* Called at initialization time */
return ONLP_STATUS_OK;
}
int
onlp_sfpi_bitmap_get(onlp_sfp_bitmap_t* bmap)
{
/*
* Ports {0, 16}
*/
int p;
AIM_BITMAP_CLR_ALL(bmap);
for(p = 0; p < NUM_OF_SFP_PORT; p++) {
AIM_BITMAP_SET(bmap, p);
}
return ONLP_STATUS_OK;
}
int
onlp_sfpi_is_present(int port)
{
/*
* Return 1 if present.
* Return 0 if not present.
* Return < 0 if error.
*/
int present;
if (onlp_file_read_int(&present, QSFP_PORT_FORMAT, QSFP_BUS_INDEX(port), "sfp_is_present") < 0) {
AIM_LOG_ERROR("Unable to read present status from port(%d)\r\n", port);
return ONLP_STATUS_E_INTERNAL;
}
return present;
}
int
onlp_sfpi_presence_bitmap_get(onlp_sfp_bitmap_t* dst)
{
uint32_t bytes[8];
char path[64] = {0};
FILE* fp;
sprintf(path, QSFP_PORT_FORMAT, QSFP_BUS_INDEX(0), "sfp_is_present_all");
fp = fopen(path, "r");
if(fp == NULL) {
AIM_LOG_ERROR("Unable to open the sfp_is_present_all device file.");
return ONLP_STATUS_E_INTERNAL;
}
int count = fscanf(fp, "%x %x %x %x %x %x %x %x",
bytes+0, bytes+1, bytes+2, bytes+3,
bytes+4, bytes+5, bytes+6, bytes+7);
fclose(fp);
if(count != AIM_ARRAYSIZE(bytes)) {
/* Likely a CPLD read timeout. */
AIM_LOG_ERROR("Unable to read all fields from the sfp_is_present_all device file.");
return ONLP_STATUS_E_INTERNAL;
}
/* Convert to 64 bit integer in port order */
int i = 0;
uint32_t presence_all = 0 ;
for(i = AIM_ARRAYSIZE(bytes)-1; i >= 0; i--) {
presence_all <<= 8;
presence_all |= bytes[i];
}
/* Populate bitmap */
for(i = 0; presence_all; i++) {
AIM_BITMAP_MOD(dst, i, (presence_all & 1));
presence_all >>= 1;
}
return ONLP_STATUS_OK;
}
int
onlp_sfpi_eeprom_read(int port, uint8_t data[256])
{
int size = 0;
if(onlp_file_read(data, 256, &size, QSFP_PORT_FORMAT, QSFP_BUS_INDEX(port), "sfp_eeprom") == ONLP_STATUS_OK) {
if(size == 256) {
return ONLP_STATUS_OK;
}
}
return ONLP_STATUS_E_INTERNAL;
}
int
onlp_sfpi_dev_readb(int port, uint8_t devaddr, uint8_t addr)
{
int bus = QSFP_BUS_INDEX(port);
return onlp_i2c_readb(bus, devaddr, addr, ONLP_I2C_F_FORCE);
}
int
onlp_sfpi_dev_writeb(int port, uint8_t devaddr, uint8_t addr, uint8_t value)
{
int bus = QSFP_BUS_INDEX(port);
return onlp_i2c_writeb(bus, devaddr, addr, value, ONLP_I2C_F_FORCE);
}
int
onlp_sfpi_dev_readw(int port, uint8_t devaddr, uint8_t addr)
{
int bus = QSFP_BUS_INDEX(port);
return onlp_i2c_readw(bus, devaddr, addr, ONLP_I2C_F_FORCE);
}
int
onlp_sfpi_dev_writew(int port, uint8_t devaddr, uint8_t addr, uint16_t value)
{
int bus = QSFP_BUS_INDEX(port);
return onlp_i2c_writew(bus, devaddr, addr, value, ONLP_I2C_F_FORCE);
}
int
onlp_sfpi_denit(void)
{
return ONLP_STATUS_OK;
}

View File

@@ -0,0 +1,336 @@
/************************************************************
* <bsn.cl fy=2014 v=onl>
*
* Copyright 2014 Big Switch Networks, Inc.
* Copyright 2017 Accton Technology Corporation.
*
* Licensed under the Eclipse Public License, Version 1.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.eclipse.org/legal/epl-v10.html
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND,
* either express or implied. See the License for the specific
* language governing permissions and limitations under the
* License.
*
* </bsn.cl>
************************************************************
*
*
*
***********************************************************/
#include <unistd.h>
#include <fcntl.h>
#include <onlplib/file.h>
#include <onlp/platformi/sysi.h>
#include <onlp/platformi/ledi.h>
#include <onlp/platformi/thermali.h>
#include <onlp/platformi/fani.h>
#include <onlp/platformi/psui.h>
#include "platform_lib.h"
#include "x86_64_accton_as7816_64x_int.h"
#include "x86_64_accton_as7816_64x_log.h"
#define CPLD_VERSION_FORMAT "/sys/bus/i2c/devices/%s/version"
#define NUM_OF_CPLD 4
static char* cpld_path[NUM_OF_CPLD] =
{
"19-0060",
"20-0062",
"21-0064",
"22-0066"
};
const char*
onlp_sysi_platform_get(void)
{
return "x86-64-accton-as7816-64x-r0";
}
int
onlp_sysi_onie_data_get(uint8_t** data, int* size)
{
uint8_t* rdata = aim_zmalloc(256);
if(onlp_file_read(rdata, 256, size, IDPROM_PATH) == ONLP_STATUS_OK) {
if(*size == 256) {
*data = rdata;
return ONLP_STATUS_OK;
}
}
aim_free(rdata);
*size = 0;
return ONLP_STATUS_E_INTERNAL;
}
int
onlp_sysi_oids_get(onlp_oid_t* table, int max)
{
int i;
onlp_oid_t* e = table;
memset(table, 0, max*sizeof(onlp_oid_t));
/* 5 Thermal sensors on the chassis */
for (i = 1; i <= CHASSIS_THERMAL_COUNT; i++) {
*e++ = ONLP_THERMAL_ID_CREATE(i);
}
/* 5 LEDs on the chassis */
for (i = 1; i <= CHASSIS_LED_COUNT; i++) {
*e++ = ONLP_LED_ID_CREATE(i);
}
/* 1 PSUs on the chassis */
for (i = 1; i <= CHASSIS_PSU_COUNT; i++) {
*e++ = ONLP_PSU_ID_CREATE(i);
}
/* 2 Fans on the chassis */
for (i = 1; i <= CHASSIS_FAN_COUNT; i++) {
*e++ = ONLP_FAN_ID_CREATE(i);
}
return 0;
}
int
onlp_sysi_platform_info_get(onlp_platform_info_t* pi)
{
int i, v[NUM_OF_CPLD] = {0};
for (i = 0; i < AIM_ARRAYSIZE(cpld_path); i++) {
v[i] = 0;
if(onlp_file_read_int(v+i, CPLD_VERSION_FORMAT , cpld_path[i]) < 0) {
return ONLP_STATUS_E_INTERNAL;
}
}
pi->cpld_versions = aim_fstrdup("%d.%d.%d.%d", v[0], v[1], v[2], v[3]);
return ONLP_STATUS_OK;
}
void
onlp_sysi_platform_info_free(onlp_platform_info_t* pi)
{
aim_free(pi->cpld_versions);
}
int
onlp_sysi_platform_manage_init(void)
{
return 0;
}
#define FAN_DUTY_MAX (100)
#define FAN_DUTY_MIN (52)
static int
sysi_fanctrl_fan_fault_policy(onlp_fan_info_t fi[CHASSIS_FAN_COUNT],
onlp_thermal_info_t ti[CHASSIS_THERMAL_COUNT],
int *adjusted)
{
int i;
*adjusted = 0;
/* Bring fan speed to FAN_DUTY_MAX if any fan is not operational */
for (i = 0; i < CHASSIS_FAN_COUNT; i++) {
if (!(fi[i].status & ONLP_FAN_STATUS_FAILED)) {
continue;
}
*adjusted = 1;
return onlp_fani_percentage_set(ONLP_FAN_ID_CREATE(1), FAN_DUTY_MAX);
}
return ONLP_STATUS_OK;
}
static int
sysi_fanctrl_fan_absent_policy(onlp_fan_info_t fi[CHASSIS_FAN_COUNT],
onlp_thermal_info_t ti[CHASSIS_THERMAL_COUNT],
int *adjusted)
{
int i;
*adjusted = 0;
/* Bring fan speed to FAN_DUTY_MAX if fan is not present */
for (i = 0; i < CHASSIS_FAN_COUNT; i++) {
if (fi[i].status & ONLP_FAN_STATUS_PRESENT) {
continue;
}
*adjusted = 1;
return onlp_fani_percentage_set(ONLP_FAN_ID_CREATE(1), FAN_DUTY_MAX);
}
return ONLP_STATUS_OK;
}
static int
sysi_fanctrl_fan_unknown_speed_policy(onlp_fan_info_t fi[CHASSIS_FAN_COUNT],
onlp_thermal_info_t ti[CHASSIS_THERMAL_COUNT],
int *adjusted)
{
int i, match = 0;
int fanduty;
int legal_duties[] = {FAN_DUTY_MIN, 64, 76, 88, FAN_DUTY_MAX};
*adjusted = 0;
if (onlp_file_read_int(&fanduty, FAN_NODE(fan_duty_cycle_percentage)) < 0) {
*adjusted = 1;
return onlp_fani_percentage_set(ONLP_FAN_ID_CREATE(1), FAN_DUTY_MIN);
}
/* Bring fan speed to min if current speed is not expected
*/
for (i = 0; i < AIM_ARRAYSIZE(legal_duties); i++) {
if (fanduty != legal_duties[i]) {
continue;
}
match = 1;
break;
}
if (!match) {
*adjusted = 1;
return onlp_fani_percentage_set(ONLP_FAN_ID_CREATE(1), FAN_DUTY_MIN);
}
return ONLP_STATUS_OK;
}
static int
sysi_fanctrl_overall_thermal_sensor_policy(onlp_fan_info_t fi[CHASSIS_FAN_COUNT],
onlp_thermal_info_t ti[CHASSIS_THERMAL_COUNT],
int *adjusted)
{
int i, num_of_sensor = 0, temp_avg = 0;
for (i = (THERMAL_1_ON_MAIN_BROAD); i <= (THERMAL_6_ON_MAIN_BROAD); i++) {
num_of_sensor++;
temp_avg += ti[i-1].mcelsius;
}
temp_avg /= num_of_sensor;
*adjusted = 1;
if (temp_avg > 57000) {
return onlp_fani_percentage_set(ONLP_FAN_ID_CREATE(1), FAN_DUTY_MAX);
}
else if (temp_avg > 52000) {
return onlp_fani_percentage_set(ONLP_FAN_ID_CREATE(1), 88);
}
else if (temp_avg > 46000) {
return onlp_fani_percentage_set(ONLP_FAN_ID_CREATE(1), 76);
}
else if (temp_avg > 43000) {
return onlp_fani_percentage_set(ONLP_FAN_ID_CREATE(1), 64);
}
return onlp_fani_percentage_set(ONLP_FAN_ID_CREATE(1), FAN_DUTY_MIN);
}
typedef int (*fan_control_policy)(onlp_fan_info_t fi[CHASSIS_FAN_COUNT],
onlp_thermal_info_t ti[CHASSIS_THERMAL_COUNT],
int *adjusted);
fan_control_policy fan_control_policies[] = {
sysi_fanctrl_fan_fault_policy,
sysi_fanctrl_fan_absent_policy,
sysi_fanctrl_fan_unknown_speed_policy,
sysi_fanctrl_overall_thermal_sensor_policy,
};
int
onlp_sysi_platform_manage_fans(void)
{
int i, rc;
onlp_fan_info_t fi[CHASSIS_FAN_COUNT];
onlp_thermal_info_t ti[CHASSIS_THERMAL_COUNT];
memset(fi, 0, sizeof(fi));
memset(ti, 0, sizeof(ti));
/* Get fan status
*/
for (i = 0; i < CHASSIS_FAN_COUNT; i++) {
rc = onlp_fani_info_get(ONLP_FAN_ID_CREATE(i+1), &fi[i]);
if (rc != ONLP_STATUS_OK) {
onlp_fani_percentage_set(ONLP_FAN_ID_CREATE(1), FAN_DUTY_MAX);
AIM_LOG_ERROR("Unable to get fan(%d) status\r\n", i+1);
return ONLP_STATUS_E_INTERNAL;
}
}
/* Get thermal sensor status
*/
for (i = 0; i < CHASSIS_THERMAL_COUNT; i++) {
rc = onlp_thermali_info_get(ONLP_THERMAL_ID_CREATE(i+1), &ti[i]);
if (rc != ONLP_STATUS_OK) {
onlp_fani_percentage_set(ONLP_FAN_ID_CREATE(1), FAN_DUTY_MAX);
AIM_LOG_ERROR("Unable to get thermal(%d) status\r\n", i+1);
return ONLP_STATUS_E_INTERNAL;
}
}
/* Apply thermal policy according the policy list,
* If fan duty is adjusted by one of the policies, skip the others
*/
for (i = 0; i < AIM_ARRAYSIZE(fan_control_policies); i++) {
int adjusted = 0;
rc = fan_control_policies[i](fi, ti, &adjusted);
if (!adjusted) {
continue;
}
return rc;
}
return ONLP_STATUS_OK;
}
int
onlp_sysi_platform_manage_leds(void)
{
int i = 0, fan_fault = 0;
/* Get each fan status
*/
for (i = 1; i <= CHASSIS_FAN_COUNT; i++)
{
onlp_fan_info_t fan_info;
if (onlp_fani_info_get(ONLP_FAN_ID_CREATE(i), &fan_info) != ONLP_STATUS_OK) {
AIM_LOG_ERROR("Unable to get fan(%d) status\r\n", i);
return ONLP_STATUS_E_INTERNAL;
}
if (!(fan_info.status & ONLP_FAN_STATUS_PRESENT)) {
AIM_LOG_ERROR("Fan(%d) is not present, set the fan system led as orange\r\n", i);
fan_fault = 1;
break;
}
if (fan_info.status & ONLP_FAN_STATUS_FAILED) {
AIM_LOG_ERROR("Fan(%d) is not working, set the fan system led as orange\r\n", i);
fan_fault = 1;
break;
}
}
return fan_fault ? onlp_ledi_mode_set(ONLP_LED_ID_CREATE(LED_FAN), ONLP_LED_MODE_ORANGE) :
onlp_ledi_mode_set(ONLP_LED_ID_CREATE(LED_FAN), ONLP_LED_MODE_GREEN);
}

View File

@@ -0,0 +1,139 @@
/************************************************************
* <bsn.cl fy=2014 v=onl>
*
* Copyright 2014 Big Switch Networks, Inc.
* Copyright 2014 Accton Technology Corporation.
*
* Licensed under the Eclipse Public License, Version 1.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.eclipse.org/legal/epl-v10.html
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND,
* either express or implied. See the License for the specific
* language governing permissions and limitations under the
* License.
*
* </bsn.cl>
************************************************************
*
* Thermal Sensor Platform Implementation.
*
***********************************************************/
#include <onlplib/file.h>
#include <onlp/platformi/thermali.h>
#include "platform_lib.h"
#define VALIDATE(_id) \
do { \
if(!ONLP_OID_IS_THERMAL(_id)) { \
return ONLP_STATUS_E_INVALID; \
} \
} while(0)
static char* devfiles__[] = /* must map with onlp_thermal_id */
{
"reserved",
NULL, /* CPU_CORE files */
"/sys/bus/i2c/devices/18-0048*temp1_input",
"/sys/bus/i2c/devices/18-0049*temp1_input",
"/sys/bus/i2c/devices/18-004a*temp1_input",
"/sys/bus/i2c/devices/18-004b*temp1_input",
"/sys/bus/i2c/devices/17-004d*temp1_input",
"/sys/bus/i2c/devices/17-004e*temp1_input",
"/sys/bus/i2c/devices/10-005b*psu_temp1_input",
"/sys/bus/i2c/devices/9-0058*psu_temp1_input",
};
static char* cpu_coretemp_files[] =
{
"/sys/devices/platform/coretemp.0*temp2_input",
"/sys/devices/platform/coretemp.0*temp3_input",
"/sys/devices/platform/coretemp.0*temp4_input",
"/sys/devices/platform/coretemp.0*temp5_input",
NULL,
};
/* Static values */
static onlp_thermal_info_t linfo[] = {
{ }, /* Not used */
{ { ONLP_THERMAL_ID_CREATE(THERMAL_CPU_CORE), "CPU Core", 0},
ONLP_THERMAL_STATUS_PRESENT,
ONLP_THERMAL_CAPS_ALL, 0, ONLP_THERMAL_THRESHOLD_INIT_DEFAULTS
},
{ { ONLP_THERMAL_ID_CREATE(THERMAL_1_ON_MAIN_BROAD), "Chassis Thermal Sensor 1", 0},
ONLP_THERMAL_STATUS_PRESENT,
ONLP_THERMAL_CAPS_ALL, 0, ONLP_THERMAL_THRESHOLD_INIT_DEFAULTS
},
{ { ONLP_THERMAL_ID_CREATE(THERMAL_2_ON_MAIN_BROAD), "Chassis Thermal Sensor 2", 0},
ONLP_THERMAL_STATUS_PRESENT,
ONLP_THERMAL_CAPS_ALL, 0, ONLP_THERMAL_THRESHOLD_INIT_DEFAULTS
},
{ { ONLP_THERMAL_ID_CREATE(THERMAL_3_ON_MAIN_BROAD), "Chassis Thermal Sensor 3", 0},
ONLP_THERMAL_STATUS_PRESENT,
ONLP_THERMAL_CAPS_ALL, 0, ONLP_THERMAL_THRESHOLD_INIT_DEFAULTS
},
{ { ONLP_THERMAL_ID_CREATE(THERMAL_4_ON_MAIN_BROAD), "Chassis Thermal Sensor 4", 0},
ONLP_THERMAL_STATUS_PRESENT,
ONLP_THERMAL_CAPS_ALL, 0, ONLP_THERMAL_THRESHOLD_INIT_DEFAULTS
},
{ { ONLP_THERMAL_ID_CREATE(THERMAL_5_ON_MAIN_BROAD), "Chassis Thermal Sensor 5", 0},
ONLP_THERMAL_STATUS_PRESENT,
ONLP_THERMAL_CAPS_ALL, 0, ONLP_THERMAL_THRESHOLD_INIT_DEFAULTS
},
{ { ONLP_THERMAL_ID_CREATE(THERMAL_6_ON_MAIN_BROAD), "Chassis Thermal Sensor 6", 0},
ONLP_THERMAL_STATUS_PRESENT,
ONLP_THERMAL_CAPS_ALL, 0, ONLP_THERMAL_THRESHOLD_INIT_DEFAULTS
},
{ { ONLP_THERMAL_ID_CREATE(THERMAL_1_ON_PSU1), "PSU-1 Thermal Sensor 1", ONLP_PSU_ID_CREATE(PSU1_ID)},
ONLP_THERMAL_STATUS_PRESENT,
ONLP_THERMAL_CAPS_ALL, 0, ONLP_THERMAL_THRESHOLD_INIT_DEFAULTS
},
{ { ONLP_THERMAL_ID_CREATE(THERMAL_1_ON_PSU2), "PSU-2 Thermal Sensor 1", ONLP_PSU_ID_CREATE(PSU2_ID)},
ONLP_THERMAL_STATUS_PRESENT,
ONLP_THERMAL_CAPS_ALL, 0, ONLP_THERMAL_THRESHOLD_INIT_DEFAULTS
}
};
/*
* This will be called to intiialize the thermali subsystem.
*/
int
onlp_thermali_init(void)
{
return ONLP_STATUS_OK;
}
/*
* Retrieve the information structure for the given thermal OID.
*
* If the OID is invalid, return ONLP_E_STATUS_INVALID.
* If an unexpected error occurs, return ONLP_E_STATUS_INTERNAL.
* Otherwise, return ONLP_STATUS_OK with the OID's information.
*
* Note -- it is expected that you fill out the information
* structure even if the sensor described by the OID is not present.
*/
int
onlp_thermali_info_get(onlp_oid_t id, onlp_thermal_info_t* info)
{
int tid;
VALIDATE(id);
tid = ONLP_OID_ID_GET(id);
/* Set the onlp_oid_hdr_t and capabilities */
*info = linfo[tid];
if(tid == THERMAL_CPU_CORE) {
int rv = onlp_file_read_int_max(&info->mcelsius, cpu_coretemp_files);
return rv;
}
return onlp_file_read_int(&info->mcelsius, devfiles__[tid]);
}

View File

@@ -0,0 +1,81 @@
/**************************************************************************//**
*
*
*
*****************************************************************************/
#include <x86_64_accton_as7816_64x/x86_64_accton_as7816_64x_config.h>
/* <auto.start.cdefs(x86_64_accton_as7816_64x_CONFIG_HEADER).source> */
#define __x86_64_accton_as7816_64x_config_STRINGIFY_NAME(_x) #_x
#define __x86_64_accton_as7816_64x_config_STRINGIFY_VALUE(_x) __x86_64_accton_as7816_64x_config_STRINGIFY_NAME(_x)
x86_64_accton_as7816_64x_config_settings_t x86_64_accton_as7816_64x_config_settings[] =
{
#ifdef X86_64_ACCTON_AS7816_64X_CONFIG_INCLUDE_LOGGING
{ __x86_64_accton_as7816_64x_config_STRINGIFY_NAME(X86_64_ACCTON_AS7816_64X_CONFIG_INCLUDE_LOGGING), __x86_64_accton_as7816_64x_config_STRINGIFY_VALUE(X86_64_ACCTON_AS7816_64X_CONFIG_INCLUDE_LOGGING) },
#else
{ X86_64_ACCTON_AS7816_64X_CONFIG_INCLUDE_LOGGING(__x86_64_accton_as7816_64x_config_STRINGIFY_NAME), "__undefined__" },
#endif
#ifdef X86_64_ACCTON_AS7816_64X_CONFIG_LOG_OPTIONS_DEFAULT
{ __x86_64_accton_as7816_64x_config_STRINGIFY_NAME(X86_64_ACCTON_AS7816_64X_CONFIG_LOG_OPTIONS_DEFAULT), __x86_64_accton_as7816_64x_config_STRINGIFY_VALUE(X86_64_ACCTON_AS7816_64X_CONFIG_LOG_OPTIONS_DEFAULT) },
#else
{ X86_64_ACCTON_AS7816_64X_CONFIG_LOG_OPTIONS_DEFAULT(__x86_64_accton_as7816_64x_config_STRINGIFY_NAME), "__undefined__" },
#endif
#ifdef X86_64_ACCTON_AS7816_64X_CONFIG_LOG_BITS_DEFAULT
{ __x86_64_accton_as7816_64x_config_STRINGIFY_NAME(X86_64_ACCTON_AS7816_64X_CONFIG_LOG_BITS_DEFAULT), __x86_64_accton_as7816_64x_config_STRINGIFY_VALUE(X86_64_ACCTON_AS7816_64X_CONFIG_LOG_BITS_DEFAULT) },
#else
{ X86_64_ACCTON_AS7816_64X_CONFIG_LOG_BITS_DEFAULT(__x86_64_accton_as7816_64x_config_STRINGIFY_NAME), "__undefined__" },
#endif
#ifdef X86_64_ACCTON_AS7816_64X_CONFIG_LOG_CUSTOM_BITS_DEFAULT
{ __x86_64_accton_as7816_64x_config_STRINGIFY_NAME(X86_64_ACCTON_AS7816_64X_CONFIG_LOG_CUSTOM_BITS_DEFAULT), __x86_64_accton_as7816_64x_config_STRINGIFY_VALUE(X86_64_ACCTON_AS7816_64X_CONFIG_LOG_CUSTOM_BITS_DEFAULT) },
#else
{ X86_64_ACCTON_AS7816_64X_CONFIG_LOG_CUSTOM_BITS_DEFAULT(__x86_64_accton_as7816_64x_config_STRINGIFY_NAME), "__undefined__" },
#endif
#ifdef X86_64_ACCTON_AS7816_64X_CONFIG_PORTING_STDLIB
{ __x86_64_accton_as7816_64x_config_STRINGIFY_NAME(X86_64_ACCTON_AS7816_64X_CONFIG_PORTING_STDLIB), __x86_64_accton_as7816_64x_config_STRINGIFY_VALUE(X86_64_ACCTON_AS7816_64X_CONFIG_PORTING_STDLIB) },
#else
{ X86_64_ACCTON_AS7816_64X_CONFIG_PORTING_STDLIB(__x86_64_accton_as7816_64x_config_STRINGIFY_NAME), "__undefined__" },
#endif
#ifdef X86_64_ACCTON_AS7816_64X_CONFIG_PORTING_INCLUDE_STDLIB_HEADERS
{ __x86_64_accton_as7816_64x_config_STRINGIFY_NAME(X86_64_ACCTON_AS7816_64X_CONFIG_PORTING_INCLUDE_STDLIB_HEADERS), __x86_64_accton_as7816_64x_config_STRINGIFY_VALUE(X86_64_ACCTON_AS7816_64X_CONFIG_PORTING_INCLUDE_STDLIB_HEADERS) },
#else
{ X86_64_ACCTON_AS7816_64X_CONFIG_PORTING_INCLUDE_STDLIB_HEADERS(__x86_64_accton_as7816_64x_config_STRINGIFY_NAME), "__undefined__" },
#endif
#ifdef X86_64_ACCTON_AS7816_64X_CONFIG_INCLUDE_UCLI
{ __x86_64_accton_as7816_64x_config_STRINGIFY_NAME(X86_64_ACCTON_AS7816_64X_CONFIG_INCLUDE_UCLI), __x86_64_accton_as7816_64x_config_STRINGIFY_VALUE(X86_64_ACCTON_AS7816_64X_CONFIG_INCLUDE_UCLI) },
#else
{ X86_64_ACCTON_AS7816_64X_CONFIG_INCLUDE_UCLI(__x86_64_accton_as7816_64x_config_STRINGIFY_NAME), "__undefined__" },
#endif
#ifdef X86_64_ACCTON_AS7816_64X_CONFIG_INCLUDE_DEFAULT_FAN_DIRECTION
{ __x86_64_accton_as7816_64x_config_STRINGIFY_NAME(X86_64_ACCTON_AS7816_64X_CONFIG_INCLUDE_DEFAULT_FAN_DIRECTION), __x86_64_accton_as7816_64x_config_STRINGIFY_VALUE(X86_64_ACCTON_AS7816_64X_CONFIG_INCLUDE_DEFAULT_FAN_DIRECTION) },
#else
{ X86_64_ACCTON_AS7816_64X_CONFIG_INCLUDE_DEFAULT_FAN_DIRECTION(__x86_64_accton_as7816_64x_config_STRINGIFY_NAME), "__undefined__" },
#endif
{ NULL, NULL }
};
#undef __x86_64_accton_as7816_64x_config_STRINGIFY_VALUE
#undef __x86_64_accton_as7816_64x_config_STRINGIFY_NAME
const char*
x86_64_accton_as7816_64x_config_lookup(const char* setting)
{
int i;
for(i = 0; x86_64_accton_as7816_64x_config_settings[i].name; i++) {
if(strcmp(x86_64_accton_as7816_64x_config_settings[i].name, setting)) {
return x86_64_accton_as7816_64x_config_settings[i].value;
}
}
return NULL;
}
int
x86_64_accton_as7816_64x_config_show(struct aim_pvs_s* pvs)
{
int i;
for(i = 0; x86_64_accton_as7816_64x_config_settings[i].name; i++) {
aim_printf(pvs, "%s = %s\n", x86_64_accton_as7816_64x_config_settings[i].name, x86_64_accton_as7816_64x_config_settings[i].value);
}
return i;
}
/* <auto.end.cdefs(x86_64_accton_as7816_64x_CONFIG_HEADER).source> */

View File

@@ -0,0 +1,10 @@
/**************************************************************************//**
*
*
*
*****************************************************************************/
#include <x86_64_accton_as7816_64x/x86_64_accton_as7816_64x_config.h>
/* <--auto.start.enum(ALL).source> */
/* <auto.end.enum(ALL).source> */

View File

@@ -0,0 +1,12 @@
/**************************************************************************//**
*
* x86_64_accton_as7816_64x Internal Header
*
*****************************************************************************/
#ifndef __x86_64_accton_as7816_64x_INT_H__
#define __x86_64_accton_as7816_64x_INT_H__
#include <x86_64_accton_as7816_64x/x86_64_accton_as7816_64x_config.h>
#endif /* __x86_64_accton_as7816_64x_INT_H__ */

View File

@@ -0,0 +1,18 @@
/**************************************************************************//**
*
*
*
*****************************************************************************/
#include <x86_64_accton_as7816_64x/x86_64_accton_as7816_64x_config.h>
#include "x86_64_accton_as7816_64x_log.h"
/*
* x86_64_accton_as7816_64x log struct.
*/
AIM_LOG_STRUCT_DEFINE(
X86_64_ACCTON_AS7816_64X_CONFIG_LOG_OPTIONS_DEFAULT,
X86_64_ACCTON_AS7816_64X_CONFIG_LOG_BITS_DEFAULT,
NULL, /* Custom log map */
X86_64_ACCTON_AS7816_64X_CONFIG_LOG_CUSTOM_BITS_DEFAULT
);

View File

@@ -0,0 +1,12 @@
/**************************************************************************//**
*
*
*
*****************************************************************************/
#ifndef __x86_64_accton_as7816_64x_LOG_H__
#define __x86_64_accton_as7816_64x_LOG_H__
#define AIM_LOG_MODULE_NAME x86_64_accton_as7816_64x
#include <AIM/aim_log.h>
#endif /* __x86_64_accton_as7816_64x_LOG_H__ */

View File

@@ -0,0 +1,24 @@
/**************************************************************************//**
*
*
*
*****************************************************************************/
#include <x86_64_accton_as7816_64x/x86_64_accton_as7816_64x_config.h>
#include "x86_64_accton_as7816_64x_log.h"
static int
datatypes_init__(void)
{
#define x86_64_accton_as7816_64x_ENUMERATION_ENTRY(_enum_name, _desc) AIM_DATATYPE_MAP_REGISTER(_enum_name, _enum_name##_map, _desc, AIM_LOG_INTERNAL);
#include <x86_64_accton_as7816_64x/x86_64_accton_as7816_64x.x>
return 0;
}
void __x86_64_accton_as7816_64x_module_init__(void)
{
AIM_LOG_STRUCT_REGISTER();
datatypes_init__();
}
int __onlp_platform_version__ = 1;

View File

@@ -0,0 +1,50 @@
/**************************************************************************//**
*
*
*
*****************************************************************************/
#include <x86_64_accton_as7816_64x/x86_64_accton_as7816_64x_config.h>
#if x86_64_accton_as7816_64x_CONFIG_INCLUDE_UCLI == 1
#include <uCli/ucli.h>
#include <uCli/ucli_argparse.h>
#include <uCli/ucli_handler_macros.h>
static ucli_status_t
x86_64_accton_as7816_64x_ucli_ucli__config__(ucli_context_t* uc)
{
UCLI_HANDLER_MACRO_MODULE_CONFIG(x86_64_accton_as7816_64x)
}
/* <auto.ucli.handlers.start> */
/* <auto.ucli.handlers.end> */
static ucli_module_t
x86_64_accton_as7816_64x_ucli_module__ =
{
"x86_64_accton_as7816_64x_ucli",
NULL,
x86_64_accton_as7816_64x_ucli_ucli_handlers__,
NULL,
NULL,
};
ucli_node_t*
x86_64_accton_as7816_64x_ucli_node_create(void)
{
ucli_node_t* n;
ucli_module_init(&x86_64_accton_as7816_64x_ucli_module__);
n = ucli_node_create("x86_64_accton_as7816_64x", NULL, &x86_64_accton_as7816_64x_ucli_module__);
ucli_node_subnode_add(n, ucli_module_log_node_create("x86_64_accton_as7816_64x"));
return n;
}
#else
void*
x86_64_accton_as7816_64x_ucli_node_create(void)
{
return NULL;
}
#endif

View File

@@ -0,0 +1 @@
include $(ONL)/make/pkg.mk

View File

@@ -0,0 +1 @@
include $(ONL)/make/pkg.mk

View File

@@ -0,0 +1 @@
!include $ONL_TEMPLATES/platform-config-platform.yml ARCH=amd64 VENDOR=accton BASENAME=x86-64-accton-as7816-64x REVISION=r0

View File

@@ -0,0 +1,33 @@
---
######################################################################
#
# platform-config for AS7816
#
######################################################################
x86-64-accton-as7816-64x-r0:
grub:
serial: >-
--port=0x3f8
--speed=115200
--word=8
--parity=no
--stop=1
kernel:
<<: *kernel-3-16
args: >-
nopat
console=ttyS0,115200n8
tg3.short_preamble=1
tg3.bcm5718s_reset=1
##network:
## interfaces:
## ma1:
## name: ~
## syspath: pci0000:00/0000:00:1c.0/0000:0a:00.0

View File

@@ -0,0 +1,129 @@
from onl.platform.base import *
from onl.platform.accton import *
class OnlPlatform_x86_64_accton_as7816_64x_r0(OnlPlatformAccton,
OnlPlatformPortConfig_64x100):
PLATFORM='x86-64-accton-as7816-64x-r0'
MODEL="AS7816-64x"
SYS_OBJECT_ID=".7816.64"
def baseconfig(self):
self.insmod("ym2651y")
self.insmod('accton_i2c_cpld')
self.insmod_platform()
########### initialize I2C bus 0 ###########
self.new_i2c_devices([
# initialize multiplexer (PCA9548)
('pca9548', 0x77, 0),
# initiate leaf multiplexer (PCA9548)
('pca9548', 0x71, 1),
('pca9548', 0x76, 1),
('pca9548', 0x73, 1),
# initiate PSU-1
('as7816_64x_psu1', 0x53, 10),
('ym2851', 0x5b, 10),
# initiate PSU-2
('as7816_64x_psu2', 0x50, 9),
('ym2851', 0x58, 9),
# initiate chassis fan
('as7816_64x_fan', 0x68, 17),
# inititate LM75
('lm75', 0x48, 18),
('lm75', 0x49, 18),
('lm75', 0x4a, 18),
('lm75', 0x4b, 18),
('lm75', 0x4d, 17),
('lm75', 0x4e, 17),
#initiate CPLD
('accton_i2c_cpld', 0x60, 19),
('accton_i2c_cpld', 0x62, 20),
('accton_i2c_cpld', 0x64, 21),
('accton_i2c_cpld', 0x66, 22),
# initiate leaf multiplexer (PCA9548)
('pca9548', 0x70, 2),
('pca9548', 0x71, 2),
('pca9548', 0x72, 2),
('pca9548', 0x73, 2),
('pca9548', 0x74, 2),
('pca9548', 0x75, 2),
('pca9548', 0x76, 2),
# initialize QSFP port 1-64
('as7816_64x_port61', 0x50, 25),
('as7816_64x_port62', 0x50, 26),
('as7816_64x_port63', 0x50, 27),
('as7816_64x_port64', 0x50, 28),
('as7816_64x_port55', 0x50, 29),
('as7816_64x_port56', 0x50, 30),
('as7816_64x_port53', 0x50, 31),
('as7816_64x_port54', 0x50, 32),
('as7816_64x_port9', 0x50, 33),
('as7816_64x_port10', 0x50, 34),
('as7816_64x_port11', 0x50, 35),
('as7816_64x_port12', 0x50, 36),
('as7816_64x_port1', 0x50, 37),
('as7816_64x_port2', 0x50, 38),
('as7816_64x_port3', 0x50, 39),
('as7816_64x_port4', 0x50, 40),
('as7816_64x_port6', 0x50, 41),
('as7816_64x_port5', 0x50, 42),
('as7816_64x_port8', 0x50, 43),
('as7816_64x_port7', 0x50, 44),
('as7816_64x_port13', 0x50, 45),
('as7816_64x_port14', 0x50, 46),
('as7816_64x_port15', 0x50, 47),
('as7816_64x_port16', 0x50, 48),
('as7816_64x_port17', 0x50, 49),
('as7816_64x_port18', 0x50, 50),
('as7816_64x_port19', 0x50, 51),
('as7816_64x_port20', 0x50, 52),
('as7816_64x_port25', 0x50, 53),
('as7816_64x_port26', 0x50, 54),
('as7816_64x_port27', 0x50, 55),
('as7816_64x_port28', 0x50, 56),
('as7816_64x_port29', 0x50, 57),
('as7816_64x_port30', 0x50, 58),
('as7816_64x_port31', 0x50, 59),
('as7816_64x_port32', 0x50, 60),
('as7816_64x_port21', 0x50, 61),
('as7816_64x_port22', 0x50, 62),
('as7816_64x_port23', 0x50, 63),
('as7816_64x_port24', 0x50, 64),
('as7816_64x_port41', 0x50, 65),
('as7816_64x_port42', 0x50, 66),
('as7816_64x_port43', 0x50, 67),
('as7816_64x_port44', 0x50, 68),
('as7816_64x_port33', 0x50, 69),
('as7816_64x_port34', 0x50, 70),
('as7816_64x_port35', 0x50, 71),
('as7816_64x_port36', 0x50, 72),
('as7816_64x_port45', 0x50, 73),
('as7816_64x_port46', 0x50, 74),
('as7816_64x_port47', 0x50, 75),
('as7816_64x_port48', 0x50, 76),
('as7816_64x_port37', 0x50, 77),
('as7816_64x_port38', 0x50, 78),
('as7816_64x_port39', 0x50, 79),
('as7816_64x_port40', 0x50, 80),
('as7816_64x_port57', 0x50, 81),
('as7816_64x_port58', 0x50, 82),
('as7816_64x_port59', 0x50, 83),
('as7816_64x_port60', 0x50, 84),
('as7816_64x_port49', 0x50, 85),
('as7816_64x_port50', 0x50, 86),
('as7816_64x_port51', 0x50, 87),
('as7816_64x_port52', 0x50, 88),
('24c02', 0x56, 0),
])
return True

View File

@@ -0,0 +1 @@
include $(ONL)/make/pkg.mk

View File

@@ -0,0 +1 @@
include $(ONL)/make/pkg.mk

View File

@@ -0,0 +1 @@
!include $ONL_TEMPLATES/platform-config-vendor.yml VENDOR=inventec Vendor=Inventec

View File

@@ -0,0 +1,7 @@
#!/usr/bin/python
from onl.platform.base import *
class OnlPlatformInventec(OnlPlatformBase):
MANUFACTURER='Inventec'
PRIVATE_ENTERPRISE_NUMBER=6569

View File

@@ -0,0 +1 @@
include $(ONL)/make/pkg.mk

View File

@@ -0,0 +1 @@
include $(ONL)/make/pkg.mk

View File

@@ -0,0 +1 @@
!include $ONL_TEMPLATES/no-arch-vendor-modules.yml ARCH=amd64 VENDOR=inventec

View File

@@ -0,0 +1 @@
include $(ONL)/make/pkg.mk

View File

@@ -0,0 +1 @@
include $(ONL)/make/pkg.mk

View File

@@ -0,0 +1 @@
!include $ONL_TEMPLATES/platform-modules.yml VENDOR=inventec BASENAME=x86-64-inventec-d7032q28b ARCH=amd64 KERNELS="onl-kernel-3.16-lts-x86-64-all:amd64"

View File

@@ -0,0 +1,6 @@
KERNELS := onl-kernel-3.16-lts-x86-64-all:amd64
KMODULES := $(wildcard *.c)
VENDOR := inventec
BASENAME := x86-64-inventec-d7032q28b
ARCH := x86_64
include $(ONL)/make/kmodule.mk

View File

@@ -0,0 +1,456 @@
/*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*/
#include <linux/module.h>
#include <linux/init.h>
#include <linux/slab.h>
#include <linux/jiffies.h>
#include <linux/i2c.h>
#include <linux/hwmon.h>
#include <linux/hwmon-sysfs.h>
#include <linux/err.h>
#include <linux/mutex.h>
//#include "I2CHostCommunication.h"
#define USE_SMBUS 1
/* definition */
#define CPLD_INFO_OFFSET 0x00
#define CPLD_RESET_OFFSET 0x08
#define CPLD_PSU_OFFSET 0x09
#define CPLD_LED_OFFSET 0x0E
#define CPLD_LED_STATU_OFFSET 0x0D
#define CPLD_CTL_OFFSET 0x0C
/* Each client has this additional data */
struct cpld_data {
struct device *hwmon_dev;
struct mutex update_lock;
};
/*-----------------------------------------------------------------------*/
static ssize_t cpld_i2c_read(struct i2c_client *client, u8 *buf, u8 offset, size_t count)
{
#if USE_SMBUS
int i;
for(i=0; i<count; i++) {
buf[i] = i2c_smbus_read_byte_data(client, offset+i);
}
return count;
#else
struct i2c_msg msg[2];
char msgbuf[2];
int status;
memset(msg, 0, sizeof(msg));
msgbuf[0] = offset;
msg[0].addr = client->addr;
msg[0].buf = msgbuf;
msg[0].len = 1;
msg[1].addr = client->addr;
msg[1].flags = I2C_M_RD;
msg[1].buf = buf;
msg[1].len = count;
status = i2c_transfer(client->adapter, msg, 2);
if(status == 2)
status = count;
return status;
#endif
}
static ssize_t cpld_i2c_write(struct i2c_client *client, char *buf, unsigned offset, size_t count)
{
#if USE_SMBUS
int i;
for(i=0; i<count; i++) {
i2c_smbus_write_byte_data(client, offset+i, buf[i]);
}
return count;
#else
struct i2c_msg msg;
int status;
u8 writebuf[64];
int i = 0;
msg.addr = client->addr;
msg.flags = 0;
/* msg.buf is u8 and casts will mask the values */
msg.buf = writebuf;
msg.buf[i++] = offset;
memcpy(&msg.buf[i], buf, count);
msg.len = i + count;
status = i2c_transfer(client->adapter, &msg, 1);
if (status == 1)
status = count;
return status;
#endif
}
/*-----------------------------------------------------------------------*/
/* sysfs attributes for hwmon */
static ssize_t show_info(struct device *dev, struct device_attribute *da,
char *buf)
{
u32 status;
//struct sensor_device_attribute *attr = to_sensor_dev_attr(da);
struct i2c_client *client = to_i2c_client(dev);
struct cpld_data *data = i2c_get_clientdata(client);
u8 b[4];
memset(b, 0, 4);
mutex_lock(&data->update_lock);
status = cpld_i2c_read(client, b, CPLD_INFO_OFFSET, 4);
mutex_unlock(&data->update_lock);
if(status != 4) return sprintf(buf, "read cpld info fail\n");
status = sprintf (buf, "The CPLD release date is %02d/%02d/%d.\n", b[2] & 0xf, (b[3] & 0x1f), 2014+(b[2] >> 4)); /* mm/dd/yyyy*/
status = sprintf (buf, "%sThe PCB version is %X%X\n", buf, b[0]>>4, b[0]&0xf);
status = sprintf (buf, "%sThe CPLD version is %d.%d\n", buf, b[1]>>4, b[1]&0xf);
return strlen(buf);
}
static ssize_t show_reset(struct device *dev, struct device_attribute *da,
char *buf)
{
u32 status;
//struct sensor_device_attribute *attr = to_sensor_dev_attr(da);
struct i2c_client *client = to_i2c_client(dev);
struct cpld_data *data = i2c_get_clientdata(client);
u8 b[1];
mutex_lock(&data->update_lock);
status = cpld_i2c_read(client, b, CPLD_RESET_OFFSET, 1);
mutex_unlock(&data->update_lock);
if(status != 1) return sprintf(buf, "read cpld reset fail\n");
status = sprintf (buf, "The CPLD 1 cpld_reset = %d\n", b[0]);
return strlen(buf);
}
static ssize_t set_reset(struct device *dev,
struct device_attribute *devattr,
const char *buf, size_t count)
{
//struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
struct i2c_client *client = to_i2c_client(dev);
struct cpld_data *data = i2c_get_clientdata(client);
u8 temp = simple_strtol(buf, NULL, 10);
mutex_lock(&data->update_lock);
cpld_i2c_write(client, &temp, CPLD_RESET_OFFSET, 1);
mutex_unlock(&data->update_lock);
return count;
}
static ssize_t show_ctl(struct device *dev, struct device_attribute *da,
char *buf)
{
u32 status;
//struct sensor_device_attribute *attr = to_sensor_dev_attr(da);
struct i2c_client *client = to_i2c_client(dev);
struct cpld_data *data = i2c_get_clientdata(client);
u8 b[1];
mutex_lock(&data->update_lock);
status = cpld_i2c_read(client, b, CPLD_CTL_OFFSET, 1);
mutex_unlock(&data->update_lock);
if(status != 1) return sprintf(buf, "read cpld ctl fail\n");
status = sprintf (buf, "0x%X\n", b[0]);
return strlen(buf);
}
static ssize_t set_ctl(struct device *dev,
struct device_attribute *devattr,
const char *buf, size_t count)
{
//struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
struct i2c_client *client = to_i2c_client(dev);
struct cpld_data *data = i2c_get_clientdata(client);
u8 byte;
u8 temp = simple_strtol(buf, NULL, 10);
mutex_lock(&data->update_lock);
cpld_i2c_read(client, &byte, CPLD_CTL_OFFSET, 1);
if(temp) byte |= (1<<0);
else byte &= ~(1<<0);
cpld_i2c_write(client, &byte, CPLD_CTL_OFFSET, 1);
mutex_unlock(&data->update_lock);
return count;
}
static char* led_str[] = {
"OFF", //000
"0.5 Hz", //001
"1 Hz", //010
"2 Hz", //011
"NA", //100
"NA", //101
"NA", //110
"ON", //111
};
static ssize_t show_led(struct device *dev, struct device_attribute *da,
char *buf)
{
u32 status;
struct sensor_device_attribute *attr = to_sensor_dev_attr(da);
struct i2c_client *client = to_i2c_client(dev);
struct cpld_data *data = i2c_get_clientdata(client);
u8 byte;
int shift = (attr->index == 0)?3:0;
mutex_lock(&data->update_lock);
status = cpld_i2c_read(client, &byte, CPLD_LED_OFFSET, 1);
mutex_unlock(&data->update_lock);
if(status != 1) return sprintf(buf, "read cpld offset 0x%x\n", CPLD_LED_OFFSET);
byte = (byte >> shift) & 0x7;
/*
0: off
1: 0.5hz
2: 1 hz
3: 2 hz
4~6: not define
7: on
*/
status = sprintf (buf, "%d: %s\n", byte, led_str[byte]);
return strlen(buf);
}
static ssize_t set_led(struct device *dev,
struct device_attribute *devattr,
const char *buf, size_t count)
{
struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
struct i2c_client *client = to_i2c_client(dev);
struct cpld_data *data = i2c_get_clientdata(client);
u8 temp = simple_strtol(buf, NULL, 16);
u8 byte;
int shift = (attr->index == 0)?3:0;
temp &= 0x7;
//validate temp value: 0,1,2,3,7, TBD
mutex_lock(&data->update_lock);
cpld_i2c_read(client, &byte, CPLD_LED_OFFSET, 1);
byte &= ~(0x7<<shift);
byte |= (temp<<shift);
cpld_i2c_write(client, &byte, CPLD_LED_OFFSET, 1);
mutex_unlock(&data->update_lock);
return count;
}
/*
CPLD report the PSU0 status
000 = PSU normal operation
100 = PSU fault
010 = PSU unpowered
111 = PSU not installed
7 6 | 5 4 3 | 2 1 0
----------------------
| psu0 | psu1
*/
static char* psu_str[] = {
"normal", //000
"NA", //001
"unpowered", //010
"NA", //011
"fault", //100
"NA", //101
"NA", //110
"not installed", //111
};
static ssize_t show_psu(struct device *dev, struct device_attribute *da,
char *buf)
{
u32 status;
struct sensor_device_attribute *attr = to_sensor_dev_attr(da);
struct i2c_client *client = to_i2c_client(dev);
struct cpld_data *data = i2c_get_clientdata(client);
u8 byte;
int shift = (attr->index == 1)?0:3;
mutex_lock(&data->update_lock);
status = cpld_i2c_read(client, &byte, CPLD_PSU_OFFSET, 1);
mutex_unlock(&data->update_lock);
byte = (byte >> shift) & 0x7;
status = sprintf (buf, "%d : %s\n", byte, psu_str[byte]);
return strlen(buf);
}
static SENSOR_DEVICE_ATTR(info, S_IRUGO, show_info, 0, 0);
static SENSOR_DEVICE_ATTR(reset, S_IWUSR|S_IRUGO, show_reset, set_reset, 0);
static SENSOR_DEVICE_ATTR(ctl, S_IWUSR|S_IRUGO, show_ctl, set_ctl, 0);
static SENSOR_DEVICE_ATTR(grn_led, S_IWUSR|S_IRUGO, show_led, set_led, 0);
static SENSOR_DEVICE_ATTR(red_led, S_IWUSR|S_IRUGO, show_led, set_led, 1);
static SENSOR_DEVICE_ATTR(psu0, S_IRUGO, show_psu, 0, 0);
static SENSOR_DEVICE_ATTR(psu1, S_IRUGO, show_psu, 0, 1);
static struct attribute *cpld_attributes[] = {
//info
&sensor_dev_attr_info.dev_attr.attr,
&sensor_dev_attr_reset.dev_attr.attr,
&sensor_dev_attr_ctl.dev_attr.attr,
&sensor_dev_attr_grn_led.dev_attr.attr,
&sensor_dev_attr_red_led.dev_attr.attr,
&sensor_dev_attr_psu0.dev_attr.attr,
&sensor_dev_attr_psu1.dev_attr.attr,
NULL
};
static const struct attribute_group cpld_group = {
.attrs = cpld_attributes,
};
/*-----------------------------------------------------------------------*/
/* device probe and removal */
static int
cpld_probe(struct i2c_client *client, const struct i2c_device_id *id)
{
struct cpld_data *data;
int status;
printk("+%s\n", __func__);
if (!i2c_check_functionality(client->adapter,
I2C_FUNC_SMBUS_BYTE_DATA | I2C_FUNC_SMBUS_WORD_DATA))
return -EIO;
data = kzalloc(sizeof(struct cpld_data), GFP_KERNEL);
if (!data)
return -ENOMEM;
i2c_set_clientdata(client, data);
mutex_init(&data->update_lock);
/* Register sysfs hooks */
status = sysfs_create_group(&client->dev.kobj, &cpld_group);
if (status)
goto exit_free;
data->hwmon_dev = hwmon_device_register(&client->dev);
if (IS_ERR(data->hwmon_dev)) {
status = PTR_ERR(data->hwmon_dev);
goto exit_remove;
}
dev_info(&client->dev, "%s: sensor '%s'\n",
dev_name(data->hwmon_dev), client->name);
return 0;
exit_remove:
sysfs_remove_group(&client->dev.kobj, &cpld_group);
exit_free:
i2c_set_clientdata(client, NULL);
kfree(data);
return status;
}
static int cpld_remove(struct i2c_client *client)
{
struct cpld_data *data = i2c_get_clientdata(client);
hwmon_device_unregister(data->hwmon_dev);
sysfs_remove_group(&client->dev.kobj, &cpld_group);
i2c_set_clientdata(client, NULL);
kfree(data);
return 0;
}
static const struct i2c_device_id cpld_ids[] = {
{ "inv_cpld", 0, },
{ /* LIST END */ }
};
MODULE_DEVICE_TABLE(i2c, cpld_ids);
static struct i2c_driver cpld_driver = {
.class = I2C_CLASS_HWMON,
.driver = {
.name = "inv_cpld",
},
.probe = cpld_probe,
.remove = cpld_remove,
.id_table = cpld_ids,
};
/*-----------------------------------------------------------------------*/
/* module glue */
static int __init inv_cpld_init(void)
{
return i2c_add_driver(&cpld_driver);
}
static void __exit inv_cpld_exit(void)
{
i2c_del_driver(&cpld_driver);
}
MODULE_AUTHOR("eddie.lan <eddie.lan@inventec>");
MODULE_DESCRIPTION("inv cpld driver");
MODULE_LICENSE("GPL");
module_init(inv_cpld_init);
module_exit(inv_cpld_exit);

View File

@@ -0,0 +1,197 @@
#include <linux/i2c.h>
//#include <linux/i2c-algo-bit.h>
#include <linux/i2c-gpio.h>
#include <linux/init.h>
#include <linux/module.h>
#include <linux/slab.h>
#include <linux/platform_device.h>
#include <linux/i2c/pca954x.h>
#include <linux/platform_data/pca953x.h>
#include <linux/platform_data/at24.h>
//#include <asm/gpio.h>
#define IO_EXPAND_BASE 64
#define IO_EXPAND_NGPIO 16
struct inv_i2c_board_info {
int ch;
int size;
struct i2c_board_info *board_info;
};
#define bus_id(id) (id)
static struct pca954x_platform_mode mux_modes_0[] = {
{.adap_id = bus_id(2),}, {.adap_id = bus_id(3),},
{.adap_id = bus_id(4),}, {.adap_id = bus_id(5),},
};
static struct pca954x_platform_mode mux_modes_0_0[] = {
{.adap_id = bus_id(6),}, {.adap_id = bus_id(7),},
{.adap_id = bus_id(8),}, {.adap_id = bus_id(9),},
{.adap_id = bus_id(10),}, {.adap_id = bus_id(11),},
{.adap_id = bus_id(12),}, {.adap_id = bus_id(13),},
};
static struct pca954x_platform_mode mux_modes_0_1[] = {
{.adap_id = bus_id(14),}, {.adap_id = bus_id(15),},
{.adap_id = bus_id(16),}, {.adap_id = bus_id(17),},
{.adap_id = bus_id(18),}, {.adap_id = bus_id(19),},
{.adap_id = bus_id(20),}, {.adap_id = bus_id(21),},
};
static struct pca954x_platform_mode mux_modes_0_2[] = {
{.adap_id = bus_id(22),}, {.adap_id = bus_id(23),},
{.adap_id = bus_id(24),}, {.adap_id = bus_id(25),},
{.adap_id = bus_id(26),}, {.adap_id = bus_id(27),},
{.adap_id = bus_id(28),}, {.adap_id = bus_id(29),},
};
static struct pca954x_platform_mode mux_modes_0_3[] = {
{.adap_id = bus_id(30),}, {.adap_id = bus_id(31),},
{.adap_id = bus_id(32),}, {.adap_id = bus_id(33),},
{.adap_id = bus_id(34),}, {.adap_id = bus_id(35),},
{.adap_id = bus_id(36),}, {.adap_id = bus_id(37),},
};
static struct pca954x_platform_data mux_data_0 = {
.modes = mux_modes_0,
.num_modes = 4,
};
static struct pca954x_platform_data mux_data_0_0 = {
.modes = mux_modes_0_0,
.num_modes = 8,
};
static struct pca954x_platform_data mux_data_0_1 = {
.modes = mux_modes_0_1,
.num_modes = 8,
};
static struct pca954x_platform_data mux_data_0_2 = {
.modes = mux_modes_0_2,
.num_modes = 8,
};
static struct pca954x_platform_data mux_data_0_3 = {
.modes = mux_modes_0_3,
.num_modes = 8,
};
static struct i2c_board_info i2c_device_info0[] __initdata = {
{"inv_psoc", 0, 0x66, 0, 0, 0},//psoc
{"inv_cpld", 0, 0x55, 0, 0, 0},//cpld
{"pca9545", 0, 0x70, &mux_data_0, 0, 0},
};
static struct i2c_board_info i2c_device_info1[] __initdata = {
{"pca9545", 0, 0x70, &mux_data_0, 0, 0},
};
static struct i2c_board_info i2c_device_info2[] __initdata = {
{"pca9548", 0, 0x72, &mux_data_0_0, 0, 0},
};
static struct i2c_board_info i2c_device_info3[] __initdata = {
{"pca9548", 0, 0x72, &mux_data_0_1, 0, 0},
};
static struct i2c_board_info i2c_device_info4[] __initdata = {
{"pca9548", 0, 0x72, &mux_data_0_2, 0, 0},
};
static struct i2c_board_info i2c_device_info5[] __initdata = {
{"pca9548", 0, 0x72, &mux_data_0_3, 0, 0},
};
static struct inv_i2c_board_info i2cdev_list[] = {
{0, ARRAY_SIZE(i2c_device_info0), i2c_device_info0 }, //smbus 0
{1, ARRAY_SIZE(i2c_device_info1), i2c_device_info1 }, //smbus 1 or gpio11+12
{bus_id(2), ARRAY_SIZE(i2c_device_info2), i2c_device_info2 }, //mux 0
{bus_id(3), ARRAY_SIZE(i2c_device_info3), i2c_device_info3 }, //mux 1
{bus_id(4), ARRAY_SIZE(i2c_device_info4), i2c_device_info4 }, //mux 2
{bus_id(5), ARRAY_SIZE(i2c_device_info5), i2c_device_info5 }, //mux 3
};
/////////////////////////////////////////////////////////////////////////////////////////
static struct i2c_gpio_platform_data i2c_gpio_platdata0 = {
.scl_pin = 8,
.sda_pin = 9,
.udelay = 5, //5:100kHz
.sda_is_open_drain = 0,
.scl_is_open_drain = 0,
.scl_is_output_only = 0
};
static struct i2c_gpio_platform_data i2c_gpio_platdata1 = {
.scl_pin = 12,
.sda_pin = 11,
.udelay = 5, //5:100kHz
.sda_is_open_drain = 0,
.scl_is_open_drain = 0,
.scl_is_output_only = 0
};
static struct platform_device device_i2c_gpio0 = {
.name = "i2c-gpio",
.id = 0, // adapter number
.dev.platform_data = &i2c_gpio_platdata0,
};
static struct platform_device device_i2c_gpio1 = {
.name = "i2c-gpio",
.id = 1, // adapter number
.dev.platform_data = &i2c_gpio_platdata1,
};
static int __init plat_redwood_x86_init(void)
{
struct i2c_adapter *adap = NULL;
struct i2c_client *e = NULL;
int ret = 0;
int i,j;
printk("el6661 plat_redwood_x86_init \n");
#if 0 //disable for ICOS
//use i2c-gpio
//register i2c gpio
//config gpio8,9 to gpio function
outl( inl(0x500) | (1<<8 | 1<<9), 0x500);
ret = platform_device_register(&device_i2c_gpio0);
if (ret) {
printk(KERN_ERR "i2c-gpio: device_i2c_gpio0 register fail %d\n", ret);
}
outl( inl(0x500) | (1<<11 | 1<<12), 0x500);
ret = platform_device_register(&device_i2c_gpio1);
if (ret) {
printk(KERN_ERR "i2c-gpio: device_i2c_gpio1 register fail %d\n", ret);
}
#endif
for(i=0; i<ARRAY_SIZE(i2cdev_list); i++) {
adap = i2c_get_adapter( i2cdev_list[i].ch );
if (adap == NULL) {
printk("redwood_x86 get channel %d adapter fail\n", i);
continue;
return -ENODEV;
}
i2c_put_adapter(adap);
for(j=0; j<i2cdev_list[i].size; j++) {
e = i2c_new_device(adap, &i2cdev_list[i].board_info[j] );
}
}
return ret;
}
module_init(plat_redwood_x86_init);
//arch_initcall(plat_redwood_x86_init);
MODULE_AUTHOR("Inventec");
MODULE_DESCRIPTION("Redwood_x86 Platform devices");
MODULE_LICENSE("GPL");

View File

@@ -0,0 +1 @@
include $(ONL)/make/pkg.mk

View File

@@ -0,0 +1 @@
!include $ONL_TEMPLATES/onlp-platform-any.yml PLATFORM=x86-64-inventec-d7032q28b ARCH=amd64 TOOLCHAIN=x86_64-linux-gnu

View File

@@ -0,0 +1,2 @@
FILTER=src
include $(ONL)/make/subdirs.mk

View File

@@ -0,0 +1,45 @@
############################################################
# <bsn.cl fy=2014 v=onl>
#
# Copyright 2014 BigSwitch Networks, Inc.
#
# Licensed under the Eclipse Public License, Version 1.0 (the
# "License"); you may not use this file except in compliance
# with the License. You may obtain a copy of the License at
#
# http://www.eclipse.org/legal/epl-v10.html
#
# Unless required by applicable law or agreed to in writing,
# software distributed under the License is distributed on an
# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND,
# either express or implied. See the License for the specific
# language governing permissions and limitations under the
# License.
#
# </bsn.cl>
############################################################
#
#
############################################################
include $(ONL)/make/config.amd64.mk
MODULE := libonlp-x86-64-inventec-d7032q28b
include $(BUILDER)/standardinit.mk
DEPENDMODULES := AIM IOF x86_64_inventec_d7032q28b onlplib
DEPENDMODULE_HEADERS := sff
include $(BUILDER)/dependmodules.mk
SHAREDLIB := libonlp-x86-64-inventec-d7032q28b.so
$(SHAREDLIB)_TARGETS := $(ALL_TARGETS)
include $(BUILDER)/so.mk
.DEFAULT_GOAL := $(SHAREDLIB)
GLOBAL_CFLAGS += -I$(onlp_BASEDIR)/module/inc
GLOBAL_CFLAGS += -DAIM_CONFIG_INCLUDE_MODULES_INIT=1
GLOBAL_CFLAGS += -fPIC
GLOBAL_LINK_LIBS += -lpthread
include $(BUILDER)/targets.mk

View File

@@ -0,0 +1,46 @@
############################################################
# <bsn.cl fy=2014 v=onl>
#
# Copyright 2014 BigSwitch Networks, Inc.
#
# Licensed under the Eclipse Public License, Version 1.0 (the
# "License"); you may not use this file except in compliance
# with the License. You may obtain a copy of the License at
#
# http://www.eclipse.org/legal/epl-v10.html
#
# Unless required by applicable law or agreed to in writing,
# software distributed under the License is distributed on an
# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND,
# either express or implied. See the License for the specific
# language governing permissions and limitations under the
# License.
#
# </bsn.cl>
############################################################
#
#
#
############################################################
include $(ONL)/make/config.amd64.mk
.DEFAULT_GOAL := onlpdump
MODULE := onlpdump
include $(BUILDER)/standardinit.mk
DEPENDMODULES := AIM IOF onlp x86_64_inventec_d7032q28b onlplib onlp_platform_defaults sff cjson cjson_util timer_wheel OS
include $(BUILDER)/dependmodules.mk
BINARY := onlpdump
$(BINARY)_LIBRARIES := $(LIBRARY_TARGETS)
include $(BUILDER)/bin.mk
GLOBAL_CFLAGS += -DAIM_CONFIG_AIM_MAIN_FUNCTION=onlpdump_main
GLOBAL_CFLAGS += -DAIM_CONFIG_INCLUDE_MODULES_INIT=1
GLOBAL_CFLAGS += -DAIM_CONFIG_INCLUDE_MAIN=1
GLOBAL_LINK_LIBS += -lpthread -lm
include $(BUILDER)/targets.mk

View File

@@ -0,0 +1 @@
name: x86_64_inventec_d7032q28b

View File

@@ -0,0 +1,9 @@
###############################################################################
#
#
#
###############################################################################
include ../../init.mk
MODULE := x86_64_inventec_d7032q28b
AUTOMODULE := x86_64_inventec_d7032q28b
include $(BUILDER)/definemodule.mk

View File

@@ -0,0 +1,9 @@
###############################################################################
#
# x86_64_inventec_d7032q28b Autogeneration
#
###############################################################################
x86_64_inventec_d7032q28b_AUTO_DEFS := module/auto/x86_64_inventec_d7032q28b.yml
x86_64_inventec_d7032q28b_AUTO_DIRS := module/inc/x86_64_inventec_d7032q28b module/src
include $(BUILDER)/auto.mk

View File

@@ -0,0 +1,50 @@
###############################################################################
#
# x86_64_inventec_d7032q28b Autogeneration Definitions.
#
###############################################################################
cdefs: &cdefs
- X86_64_INVENTEC_D7032Q28B_CONFIG_INCLUDE_LOGGING:
doc: "Include or exclude logging."
default: 1
- X86_64_INVENTEC_D7032Q28B_CONFIG_LOG_OPTIONS_DEFAULT:
doc: "Default enabled log options."
default: AIM_LOG_OPTIONS_DEFAULT
- X86_64_INVENTEC_D7032Q28B_CONFIG_LOG_BITS_DEFAULT:
doc: "Default enabled log bits."
default: AIM_LOG_BITS_DEFAULT
- X86_64_INVENTEC_D7032Q28B_CONFIG_LOG_CUSTOM_BITS_DEFAULT:
doc: "Default enabled custom log bits."
default: 0
- X86_64_INVENTEC_D7032Q28B_CONFIG_PORTING_STDLIB:
doc: "Default all porting macros to use the C standard libraries."
default: 1
- X86_64_INVENTEC_D7032Q28B_CONFIG_PORTING_INCLUDE_STDLIB_HEADERS:
doc: "Include standard library headers for stdlib porting macros."
default: X86_64_INVENTEC_D7032Q28B_CONFIG_PORTING_STDLIB
- X86_64_INVENTEC_D7032Q28B_CONFIG_INCLUDE_UCLI:
doc: "Include generic uCli support."
default: 0
- X86_64_INVENTEC_D7032Q28B_CONFIG_INCLUDE_DEFAULT_FAN_DIRECTION:
doc: "Assume chassis fan direction is the same as the PSU fan direction."
default: 0
definitions:
cdefs:
X86_64_INVENTEC_D7032Q28B_CONFIG_HEADER:
defs: *cdefs
basename: x86_64_inventec_d7032q28b_config
portingmacro:
X86_64_INVENTEC_D7032Q28B:
macros:
- malloc
- free
- memset
- memcpy
- strncpy
- vsnprintf
- snprintf
- strlen

View File

@@ -0,0 +1,14 @@
/**************************************************************************//**
*
*
*
*****************************************************************************/
#include <x86_64_inventec_d7032q28b/x86_64_inventec_d7032q28b_config.h>
/* <--auto.start.xmacro(ALL).define> */
/* <auto.end.xmacro(ALL).define> */
/* <--auto.start.xenum(ALL).define> */
/* <auto.end.xenum(ALL).define> */

View File

@@ -0,0 +1,137 @@
/**************************************************************************//**
*
* @file
* @brief x86_64_inventec_d7032q28b Configuration Header
*
* @addtogroup x86_64_inventec_d7032q28b-config
* @{
*
*****************************************************************************/
#ifndef __x86_64_inventec_d7032q28b_CONFIG_H__
#define __x86_64_inventec_d7032q28b_CONFIG_H__
#ifdef GLOBAL_INCLUDE_CUSTOM_CONFIG
#include <global_custom_config.h>
#endif
#ifdef x86_64_inventec_d7032q28b_INCLUDE_CUSTOM_CONFIG
#include <x86_64_inventec_d7032q28b_custom_config.h>
#endif
/* <auto.start.cdefs(x86_64_inventec_d7032q28b_CONFIG_HEADER).header> */
#include <AIM/aim.h>
/**
* x86_64_inventec_d7032q28b_CONFIG_INCLUDE_LOGGING
*
* Include or exclude logging. */
#ifndef x86_64_inventec_d7032q28b_CONFIG_INCLUDE_LOGGING
#define x86_64_inventec_d7032q28b_CONFIG_INCLUDE_LOGGING 1
#endif
/**
* x86_64_inventec_d7032q28b_CONFIG_LOG_OPTIONS_DEFAULT
*
* Default enabled log options. */
#ifndef x86_64_inventec_d7032q28b_CONFIG_LOG_OPTIONS_DEFAULT
#define x86_64_inventec_d7032q28b_CONFIG_LOG_OPTIONS_DEFAULT AIM_LOG_OPTIONS_DEFAULT
#endif
/**
* x86_64_inventec_d7032q28b_CONFIG_LOG_BITS_DEFAULT
*
* Default enabled log bits. */
#ifndef x86_64_inventec_d7032q28b_CONFIG_LOG_BITS_DEFAULT
#define x86_64_inventec_d7032q28b_CONFIG_LOG_BITS_DEFAULT AIM_LOG_BITS_DEFAULT
#endif
/**
* x86_64_inventec_d7032q28b_CONFIG_LOG_CUSTOM_BITS_DEFAULT
*
* Default enabled custom log bits. */
#ifndef x86_64_inventec_d7032q28b_CONFIG_LOG_CUSTOM_BITS_DEFAULT
#define x86_64_inventec_d7032q28b_CONFIG_LOG_CUSTOM_BITS_DEFAULT 0
#endif
/**
* x86_64_inventec_d7032q28b_CONFIG_PORTING_STDLIB
*
* Default all porting macros to use the C standard libraries. */
#ifndef x86_64_inventec_d7032q28b_CONFIG_PORTING_STDLIB
#define x86_64_inventec_d7032q28b_CONFIG_PORTING_STDLIB 1
#endif
/**
* x86_64_inventec_d7032q28b_CONFIG_PORTING_INCLUDE_STDLIB_HEADERS
*
* Include standard library headers for stdlib porting macros. */
#ifndef x86_64_inventec_d7032q28b_CONFIG_PORTING_INCLUDE_STDLIB_HEADERS
#define x86_64_inventec_d7032q28b_CONFIG_PORTING_INCLUDE_STDLIB_HEADERS x86_64_inventec_d7032q28b_CONFIG_PORTING_STDLIB
#endif
/**
* x86_64_inventec_d7032q28b_CONFIG_INCLUDE_UCLI
*
* Include generic uCli support. */
#ifndef x86_64_inventec_d7032q28b_CONFIG_INCLUDE_UCLI
#define x86_64_inventec_d7032q28b_CONFIG_INCLUDE_UCLI 0
#endif
/**
* x86_64_inventec_d7032q28b_CONFIG_INCLUDE_DEFAULT_FAN_DIRECTION
*
* Assume chassis fan direction is the same as the PSU fan direction. */
#ifndef x86_64_inventec_d7032q28b_CONFIG_INCLUDE_DEFAULT_FAN_DIRECTION
#define x86_64_inventec_d7032q28b_CONFIG_INCLUDE_DEFAULT_FAN_DIRECTION 0
#endif
/**
* All compile time options can be queried or displayed
*/
/** Configuration settings structure. */
typedef struct x86_64_inventec_d7032q28b_config_settings_s {
/** name */
const char* name;
/** value */
const char* value;
} x86_64_inventec_d7032q28b_config_settings_t;
/** Configuration settings table. */
/** x86_64_inventec_d7032q28b_config_settings table. */
extern x86_64_inventec_d7032q28b_config_settings_t x86_64_inventec_d7032q28b_config_settings[];
/**
* @brief Lookup a configuration setting.
* @param setting The name of the configuration option to lookup.
*/
const char* x86_64_inventec_d7032q28b_config_lookup(const char* setting);
/**
* @brief Show the compile-time configuration.
* @param pvs The output stream.
*/
int x86_64_inventec_d7032q28b_config_show(struct aim_pvs_s* pvs);
/* <auto.end.cdefs(x86_64_inventec_d7032q28b_CONFIG_HEADER).header> */
#include "x86_64_inventec_d7032q28b_porting.h"
#endif /* __x86_64_inventec_d7032q28b_CONFIG_H__ */
/* @} */

View File

@@ -0,0 +1,26 @@
/**************************************************************************//**
*
* x86_64_inventec_d7032q28b Doxygen Header
*
*****************************************************************************/
#ifndef __x86_64_inventec_d7032q28b_DOX_H__
#define __x86_64_inventec_d7032q28b_DOX_H__
/**
* @defgroup x86_64_inventec_d7032q28b x86_64_inventec_d7032q28b - x86_64_inventec_d7032q28b Description
*
The documentation overview for this module should go here.
*
* @{
*
* @defgroup x86_64_inventec_d7032q28b-x86_64_inventec_d7032q28b Public Interface
* @defgroup x86_64_inventec_d7032q28b-config Compile Time Configuration
* @defgroup x86_64_inventec_d7032q28b-porting Porting Macros
*
* @}
*
*/
#endif /* __x86_64_inventec_d7032q28b_DOX_H__ */

View File

@@ -0,0 +1,107 @@
/**************************************************************************//**
*
* @file
* @brief x86_64_inventec_d7032q28b Porting Macros.
*
* @addtogroup x86_64_inventec_d7032q28b-porting
* @{
*
*****************************************************************************/
#ifndef __x86_64_inventec_d7032q28b_PORTING_H__
#define __x86_64_inventec_d7032q28b_PORTING_H__
/* <auto.start.portingmacro(ALL).define> */
#if x86_64_inventec_d7032q28b_CONFIG_PORTING_INCLUDE_STDLIB_HEADERS == 1
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <stdarg.h>
#include <memory.h>
#endif
#ifndef x86_64_inventec_d7032q28b_MALLOC
#if defined(GLOBAL_MALLOC)
#define x86_64_inventec_d7032q28b_MALLOC GLOBAL_MALLOC
#elif x86_64_inventec_d7032q28b_CONFIG_PORTING_STDLIB == 1
#define x86_64_inventec_d7032q28b_MALLOC malloc
#else
#error The macro x86_64_inventec_d7032q28b_MALLOC is required but cannot be defined.
#endif
#endif
#ifndef x86_64_inventec_d7032q28b_FREE
#if defined(GLOBAL_FREE)
#define x86_64_inventec_d7032q28b_FREE GLOBAL_FREE
#elif x86_64_inventec_d7032q28b_CONFIG_PORTING_STDLIB == 1
#define x86_64_inventec_d7032q28b_FREE free
#else
#error The macro x86_64_inventec_d7032q28b_FREE is required but cannot be defined.
#endif
#endif
#ifndef x86_64_inventec_d7032q28b_MEMSET
#if defined(GLOBAL_MEMSET)
#define x86_64_inventec_d7032q28b_MEMSET GLOBAL_MEMSET
#elif x86_64_inventec_d7032q28b_CONFIG_PORTING_STDLIB == 1
#define x86_64_inventec_d7032q28b_MEMSET memset
#else
#error The macro x86_64_inventec_d7032q28b_MEMSET is required but cannot be defined.
#endif
#endif
#ifndef x86_64_inventec_d7032q28b_MEMCPY
#if defined(GLOBAL_MEMCPY)
#define x86_64_inventec_d7032q28b_MEMCPY GLOBAL_MEMCPY
#elif x86_64_inventec_d7032q28b_CONFIG_PORTING_STDLIB == 1
#define x86_64_inventec_d7032q28b_MEMCPY memcpy
#else
#error The macro x86_64_inventec_d7032q28b_MEMCPY is required but cannot be defined.
#endif
#endif
#ifndef x86_64_inventec_d7032q28b_STRNCPY
#if defined(GLOBAL_STRNCPY)
#define x86_64_inventec_d7032q28b_STRNCPY GLOBAL_STRNCPY
#elif x86_64_inventec_d7032q28b_CONFIG_PORTING_STDLIB == 1
#define x86_64_inventec_d7032q28b_STRNCPY strncpy
#else
#error The macro x86_64_inventec_d7032q28b_STRNCPY is required but cannot be defined.
#endif
#endif
#ifndef x86_64_inventec_d7032q28b_VSNPRINTF
#if defined(GLOBAL_VSNPRINTF)
#define x86_64_inventec_d7032q28b_VSNPRINTF GLOBAL_VSNPRINTF
#elif x86_64_inventec_d7032q28b_CONFIG_PORTING_STDLIB == 1
#define x86_64_inventec_d7032q28b_VSNPRINTF vsnprintf
#else
#error The macro x86_64_inventec_d7032q28b_VSNPRINTF is required but cannot be defined.
#endif
#endif
#ifndef x86_64_inventec_d7032q28b_SNPRINTF
#if defined(GLOBAL_SNPRINTF)
#define x86_64_inventec_d7032q28b_SNPRINTF GLOBAL_SNPRINTF
#elif x86_64_inventec_d7032q28b_CONFIG_PORTING_STDLIB == 1
#define x86_64_inventec_d7032q28b_SNPRINTF snprintf
#else
#error The macro x86_64_inventec_d7032q28b_SNPRINTF is required but cannot be defined.
#endif
#endif
#ifndef x86_64_inventec_d7032q28b_STRLEN
#if defined(GLOBAL_STRLEN)
#define x86_64_inventec_d7032q28b_STRLEN GLOBAL_STRLEN
#elif x86_64_inventec_d7032q28b_CONFIG_PORTING_STDLIB == 1
#define x86_64_inventec_d7032q28b_STRLEN strlen
#else
#error The macro x86_64_inventec_d7032q28b_STRLEN is required but cannot be defined.
#endif
#endif
/* <auto.end.portingmacro(ALL).define> */
#endif /* __x86_64_inventec_d7032q28b_PORTING_H__ */
/* @} */

View File

@@ -0,0 +1,10 @@
###############################################################################
#
#
#
###############################################################################
THIS_DIR := $(dir $(lastword $(MAKEFILE_LIST)))
x86_64_inventec_d7032q28b_INCLUDES := -I $(THIS_DIR)inc
x86_64_inventec_d7032q28b_INTERNAL_INCLUDES := -I $(THIS_DIR)src
x86_64_inventec_d7032q28b_DEPENDMODULE_ENTRIES := init:x86_64_inventec_d7032q28b ucli:x86_64_inventec_d7032q28b

View File

@@ -0,0 +1,9 @@
###############################################################################
#
# Local source generation targets.
#
###############################################################################
ucli:
@../../../../tools/uclihandlers.py x86_64_inventec_d7032q28b_ucli.c

View File

@@ -0,0 +1,329 @@
/************************************************************
* <bsn.cl fy=2014 v=onl>
*
* Copyright 2014 Big Switch Networks, Inc.
* Copyright 2014 Accton Technology Corporation.
*
* Licensed under the Eclipse Public License, Version 1.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.eclipse.org/legal/epl-v10.html
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND,
* either express or implied. See the License for the specific
* language governing permissions and limitations under the
* License.
*
* </bsn.cl>
************************************************************
*
* Fan Platform Implementation Defaults.
*
***********************************************************/
#include <onlplib/file.h>
#include <onlp/platformi/fani.h>
#include <onlplib/mmap.h>
#include <fcntl.h>
#include "platform_lib.h"
#define PREFIX_PATH_ON_MAIN_BOARD "/sys/bus/i2c/devices/2-0066/"
#define PREFIX_PATH_ON_PSU "/sys/bus/i2c/devices/"
#define MAX_FAN_SPEED 18000
#define MAX_PSU_FAN_SPEED 25500
#define PROJECT_NAME
#define LEN_FILE_NAME 80
#define FAN_RESERVED 0
#define FAN_1_ON_MAIN_BOARD 1
#define FAN_2_ON_MAIN_BOARD 2
#define FAN_3_ON_MAIN_BOARD 3
#define FAN_4_ON_MAIN_BOARD 4
#define FAN_5_ON_MAIN_BOARD 5
#define FAN_6_ON_MAIN_BOARD 6
#define FAN_1_ON_PSU1 7
#define FAN_1_ON_PSU2 8
enum fan_id {
FAN_1_ON_FAN_BOARD = 1,
FAN_2_ON_FAN_BOARD,
FAN_3_ON_FAN_BOARD,
FAN_4_ON_FAN_BOARD,
FAN_5_ON_FAN_BOARD,
FAN_1_ON_PSU_1,
FAN_1_ON_PSU_2,
};
#define _MAKE_FAN_PATH_ON_MAIN_BOARD(prj,id) \
{ #prj"fan"#id"_present", #prj"fan"#id"_fault", #prj"fan"#id"_front_speed_rpm", \
#prj"fan"#id"_direction", #prj"fan_duty_cycle_percentage", #prj"fan"#id"_rear_speed_rpm" }
#define MAKE_FAN_PATH_ON_MAIN_BOARD(prj,id) _MAKE_FAN_PATH_ON_MAIN_BOARD(prj,id)
#define MAKE_FAN_PATH_ON_PSU(folder) \
{"", #folder"/psu_fan1_fault", #folder"/psu_fan1_speed_rpm", \
"", #folder"/psu_fan1_duty_cycle_percentage", "" }
#define MAKE_FAN_INFO_NODE_ON_MAIN_BOARD(id) \
{ \
{ ONLP_FAN_ID_CREATE(FAN_##id##_ON_MAIN_BOARD), "Chassis Fan "#id, 0 }, \
0x0, \
(ONLP_FAN_CAPS_SET_PERCENTAGE | ONLP_FAN_CAPS_GET_RPM | ONLP_FAN_CAPS_GET_PERCENTAGE), \
0, \
0, \
ONLP_FAN_MODE_INVALID, \
}
#define MAKE_FAN_INFO_NODE_ON_PSU(psu_id, fan_id) \
{ \
{ ONLP_FAN_ID_CREATE(FAN_##fan_id##_ON_PSU##psu_id), "Chassis PSU-"#psu_id " Fan "#fan_id, 0 }, \
0x0, \
(ONLP_FAN_CAPS_SET_PERCENTAGE | ONLP_FAN_CAPS_GET_RPM | ONLP_FAN_CAPS_GET_PERCENTAGE), \
0, \
0, \
ONLP_FAN_MODE_INVALID, \
}
/* Static fan information */
onlp_fan_info_t linfo[] = {
{ }, /* Not used */
MAKE_FAN_INFO_NODE_ON_MAIN_BOARD(1),
MAKE_FAN_INFO_NODE_ON_MAIN_BOARD(2),
MAKE_FAN_INFO_NODE_ON_MAIN_BOARD(3),
MAKE_FAN_INFO_NODE_ON_MAIN_BOARD(4),
MAKE_FAN_INFO_NODE_ON_MAIN_BOARD(5),
MAKE_FAN_INFO_NODE_ON_MAIN_BOARD(6),
MAKE_FAN_INFO_NODE_ON_PSU(1,1),
MAKE_FAN_INFO_NODE_ON_PSU(2,1),
};
#define VALIDATE(_id) \
do { \
if(!ONLP_OID_IS_FAN(_id)) { \
return ONLP_STATUS_E_INVALID; \
} \
} while(0)
static int
_onlp_fani_info_get_fan(int fid, onlp_fan_info_t* info)
{
int value, ret;
/* get fan present status
*/
ret = onlp_file_read_int(&value, "%s""fan%d_present", FAN_BOARD_PATH, fid);
if (ret < 0) {
return ONLP_STATUS_E_INTERNAL;
}
if (value == 0) {
return ONLP_STATUS_OK;
}
info->status |= ONLP_FAN_STATUS_PRESENT;
/* get fan fault status (turn on when any one fails)
*/
ret = onlp_file_read_int(&value, "%s""fan%d_fault", FAN_BOARD_PATH, fid);
if (ret < 0) {
return ONLP_STATUS_E_INTERNAL;
}
if (value > 0) {
info->status |= ONLP_FAN_STATUS_FAILED;
}
/* get fan direction (both : the same)
*/
ret = onlp_file_read_int(&value, "%s""fan%d_direction", FAN_BOARD_PATH, fid);
if (ret < 0) {
return ONLP_STATUS_E_INTERNAL;
}
info->status |= value ? ONLP_FAN_STATUS_B2F : ONLP_FAN_STATUS_F2B;
/* get front fan speed
*/
ret = onlp_file_read_int(&value, "%s""fan%d_front_speed_rpm", FAN_BOARD_PATH, fid);
if (ret < 0) {
return ONLP_STATUS_E_INTERNAL;
}
info->rpm = value;
/* get rear fan speed
*/
ret = onlp_file_read_int(&value, "%s""fan%d_rear_speed_rpm", FAN_BOARD_PATH, fid);
if (ret < 0) {
return ONLP_STATUS_E_INTERNAL;
}
/* take the min value from front/rear fan speed
*/
if (info->rpm > value) {
info->rpm = value;
}
/* get speed percentage from rpm
*/
ret = onlp_file_read_int(&value, "%s""fan_max_speed_rpm", FAN_BOARD_PATH);
if (ret < 0) {
return ONLP_STATUS_E_INTERNAL;
}
info->percentage = (info->rpm * 100)/value;
return ONLP_STATUS_OK;
}
static uint32_t
_onlp_get_fan_direction_on_psu(void)
{
/* Try to read direction from PSU1.
* If PSU1 is not valid, read from PSU2
*/
int i = 0;
for (i = PSU1_ID; i <= PSU2_ID; i++) {
psu_type_t psu_type;
psu_type = get_psu_type(i, NULL, 0);
if (psu_type == PSU_TYPE_UNKNOWN) {
continue;
}
if (PSU_TYPE_AC_F2B == psu_type) {
return ONLP_FAN_STATUS_F2B;
}
else {
return ONLP_FAN_STATUS_B2F;
}
}
return 0;
}
static int
_onlp_fani_info_get_fan_on_psu(int pid, onlp_fan_info_t* info)
{
int val = 0;
info->status |= ONLP_FAN_STATUS_PRESENT;
/* get fan direction
*/
info->status |= _onlp_get_fan_direction_on_psu();
/* get fan fault status
*/
if (psu_pmbus_info_get(pid, "psu_fan1_fault", &val) == ONLP_STATUS_OK) {
info->status |= (val > 0) ? ONLP_FAN_STATUS_FAILED : 0;
}
/* get fan speed
*/
if (psu_pmbus_info_get(pid, "psu_fan1_speed_rpm", &val) == ONLP_STATUS_OK) {
info->rpm = val;
info->percentage = (info->rpm * 100) / MAX_PSU_FAN_SPEED;
}
return ONLP_STATUS_OK;
}
/*
* This function will be called prior to all of onlp_fani_* functions.
*/
int
onlp_fani_init(void)
{
return ONLP_STATUS_OK;
}
int
onlp_fani_info_get(onlp_oid_t id, onlp_fan_info_t* info)
{
int rc = 0;
int local_id;
VALIDATE(id);
local_id = ONLP_OID_ID_GET(id);
*info = linfo[local_id];
switch (local_id)
{
case FAN_1_ON_PSU1:
case FAN_1_ON_PSU2:
rc = _onlp_fani_info_get_fan_on_psu(local_id, info);
break;
case FAN_1_ON_MAIN_BOARD:
case FAN_2_ON_MAIN_BOARD:
case FAN_3_ON_MAIN_BOARD:
case FAN_4_ON_MAIN_BOARD:
case FAN_5_ON_MAIN_BOARD:
case FAN_6_ON_MAIN_BOARD:
rc =_onlp_fani_info_get_fan(local_id, info);
break;
default:
rc = ONLP_STATUS_E_INVALID;
break;
}
return rc;
}
/*
* This function sets the fan speed of the given OID as a percentage.
*
* This will only be called if the OID has the PERCENTAGE_SET
* capability.
*
* It is optional if you have no fans at all with this feature.
*/
int
onlp_fani_percentage_set(onlp_oid_t id, int p)
{
int fid;
char *path = NULL;
VALIDATE(id);
fid = ONLP_OID_ID_GET(id);
/* reject p=0 (p=0, stop fan) */
if (p == 0){
return ONLP_STATUS_E_INVALID;
}
switch (fid)
{
case FAN_1_ON_PSU_1:
return psu_pmbus_info_set(PSU1_ID, "psu_fan1_duty_cycle_percentage", p);
case FAN_1_ON_PSU_2:
return psu_pmbus_info_set(PSU2_ID, "psu_fan1_duty_cycle_percentage", p);
case FAN_1_ON_FAN_BOARD:
case FAN_2_ON_FAN_BOARD:
case FAN_3_ON_FAN_BOARD:
case FAN_4_ON_FAN_BOARD:
case FAN_5_ON_FAN_BOARD:
path = FAN_NODE(fan_duty_cycle_percentage);
break;
default:
return ONLP_STATUS_E_INVALID;
}
if (onlp_file_write_int(p, path, NULL) != 0) {
AIM_LOG_ERROR("Unable to write data to file (%s)\r\n", path);
return ONLP_STATUS_E_INTERNAL;
}
return ONLP_STATUS_OK;
}

View File

@@ -0,0 +1,253 @@
/************************************************************
* <bsn.cl fy=2014 v=onl>
*
* Copyright 2014 Big Switch Networks, Inc.
* Copyright 2014 Accton Technology Corporation.
*
* Licensed under the Eclipse Public License, Version 1.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.eclipse.org/legal/epl-v10.html
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND,
* either express or implied. See the License for the specific
* language governing permissions and limitations under the
* License.
*
* </bsn.cl>
************************************************************
*
*
*
***********************************************************/
#include <onlp/platformi/ledi.h>
#include <sys/mman.h>
#include <stdio.h>
#include <string.h>
#include <fcntl.h>
#include <onlplib/mmap.h>
#include <onlplib/file.h>
#include "platform_lib.h"
#define prefix_path "/sys/class/leds/inventec_d7032q28b_led::"
#define filename "brightness"
#define VALIDATE(_id) \
do { \
if(!ONLP_OID_IS_LED(_id)) { \
return ONLP_STATUS_E_INVALID; \
} \
} while(0)
/* LED related data
*/
enum onlp_led_id
{
LED_RESERVED = 0,
LED_DIAG,
LED_LOC,
LED_FAN,
LED_PSU1,
LED_PSU2
};
enum led_light_mode {
LED_MODE_OFF = 0,
LED_MODE_GREEN,
LED_MODE_AMBER,
LED_MODE_RED,
LED_MODE_BLUE,
LED_MODE_GREEN_BLINK,
LED_MODE_AMBER_BLINK,
LED_MODE_RED_BLINK,
LED_MODE_BLUE_BLINK,
LED_MODE_AUTO,
LED_MODE_UNKNOWN
};
typedef struct led_light_mode_map {
enum onlp_led_id id;
enum led_light_mode driver_led_mode;
enum onlp_led_mode_e onlp_led_mode;
} led_light_mode_map_t;
led_light_mode_map_t led_map[] = {
{LED_DIAG, LED_MODE_OFF, ONLP_LED_MODE_OFF},
{LED_DIAG, LED_MODE_GREEN, ONLP_LED_MODE_GREEN},
{LED_DIAG, LED_MODE_AMBER, ONLP_LED_MODE_ORANGE},
{LED_DIAG, LED_MODE_RED, ONLP_LED_MODE_RED},
{LED_LOC, LED_MODE_OFF, ONLP_LED_MODE_OFF},
{LED_LOC, LED_MODE_BLUE, ONLP_LED_MODE_BLUE},
{LED_FAN, LED_MODE_AUTO, ONLP_LED_MODE_AUTO},
{LED_PSU1, LED_MODE_AUTO, ONLP_LED_MODE_AUTO},
{LED_PSU2, LED_MODE_AUTO, ONLP_LED_MODE_AUTO}
};
static char last_path[][10] = /* must map with onlp_led_id */
{
"reserved",
"diag",
"loc",
"fan",
"psu1",
"psu2"
};
/*
* Get the information for the given LED OID.
*/
static onlp_led_info_t linfo[] =
{
{ }, /* Not used */
{
{ ONLP_LED_ID_CREATE(LED_DIAG), "Chassis LED 1 (DIAG LED)", 0 },
ONLP_LED_STATUS_PRESENT,
ONLP_LED_CAPS_ON_OFF | ONLP_LED_CAPS_GREEN | ONLP_LED_CAPS_RED | ONLP_LED_CAPS_ORANGE,
},
{
{ ONLP_LED_ID_CREATE(LED_LOC), "Chassis LED 2 (LOC LED)", 0 },
ONLP_LED_STATUS_PRESENT,
ONLP_LED_CAPS_ON_OFF | ONLP_LED_CAPS_BLUE,
},
{
{ ONLP_LED_ID_CREATE(LED_FAN), "Chassis LED 3 (FAN LED)", 0 },
ONLP_LED_STATUS_PRESENT,
ONLP_LED_CAPS_AUTO,
},
{
{ ONLP_LED_ID_CREATE(LED_PSU1), "Chassis LED 4 (PSU1 LED)", 0 },
ONLP_LED_STATUS_PRESENT,
ONLP_LED_CAPS_AUTO,
},
{
{ ONLP_LED_ID_CREATE(LED_PSU2), "Chassis LED 4 (PSU2 LED)", 0 },
ONLP_LED_STATUS_PRESENT,
ONLP_LED_CAPS_AUTO,
},
};
static int driver_to_onlp_led_mode(enum onlp_led_id id, enum led_light_mode driver_led_mode)
{
int i, nsize = sizeof(led_map)/sizeof(led_map[0]);
for (i = 0; i < nsize; i++)
{
if (id == led_map[i].id && driver_led_mode == led_map[i].driver_led_mode)
{
return led_map[i].onlp_led_mode;
}
}
return 0;
}
static int onlp_to_driver_led_mode(enum onlp_led_id id, onlp_led_mode_t onlp_led_mode)
{
int i, nsize = sizeof(led_map)/sizeof(led_map[0]);
for(i = 0; i < nsize; i++)
{
if (id == led_map[i].id && onlp_led_mode == led_map[i].onlp_led_mode)
{
return led_map[i].driver_led_mode;
}
}
return 0;
}
/*
* This function will be called prior to any other onlp_ledi_* functions.
*/
int
onlp_ledi_init(void)
{
/*
* Diag LED Off
*/
onlp_ledi_mode_set(ONLP_LED_ID_CREATE(LED_DIAG), ONLP_LED_MODE_OFF);
return ONLP_STATUS_OK;
}
int
onlp_ledi_info_get(onlp_oid_t id, onlp_led_info_t* info)
{
int local_id;
char data[2] = {0};
char fullpath[50] = {0};
VALIDATE(id);
local_id = ONLP_OID_ID_GET(id);
/* get fullpath */
sprintf(fullpath, "%s%s/%s", prefix_path, last_path[local_id], filename);
/* Set the onlp_oid_hdr_t and capabilities */
*info = linfo[ONLP_OID_ID_GET(id)];
/* Set LED mode */
if (onlp_file_read_string(fullpath, data, sizeof(data), 0) != 0) {
DEBUG_PRINT("%s(%d)\r\n", __FUNCTION__, __LINE__);
return ONLP_STATUS_E_INTERNAL;
}
info->mode = driver_to_onlp_led_mode(local_id, atoi(data));
/* Set the on/off status */
if (info->mode != ONLP_LED_MODE_OFF) {
info->status |= ONLP_LED_STATUS_ON;
}
return ONLP_STATUS_OK;
}
/*
* Turn an LED on or off.
*
* This function will only be called if the LED OID supports the ONOFF
* capability.
*
* What 'on' means in terms of colors or modes for multimode LEDs is
* up to the platform to decide. This is intended as baseline toggle mechanism.
*/
int
onlp_ledi_set(onlp_oid_t id, int on_or_off)
{
VALIDATE(id);
if (!on_or_off) {
return onlp_ledi_mode_set(id, ONLP_LED_MODE_OFF);
}
return ONLP_STATUS_E_UNSUPPORTED;
}
/*
* This function puts the LED into the given mode. It is a more functional
* interface for multimode LEDs.
*
* Only modes reported in the LED's capabilities will be attempted.
*/
int
onlp_ledi_mode_set(onlp_oid_t id, onlp_led_mode_t mode)
{
int local_id;
char fullpath[50] = {0};
VALIDATE(id);
local_id = ONLP_OID_ID_GET(id);
sprintf(fullpath, "%s%s/%s", prefix_path, last_path[local_id], filename);
if (onlp_file_write_int(onlp_to_driver_led_mode(local_id, mode), fullpath, NULL) != 0)
{
return ONLP_STATUS_E_INTERNAL;
}
return ONLP_STATUS_OK;
}

View File

@@ -0,0 +1,9 @@
###############################################################################
#
#
#
###############################################################################
LIBRARY := x86_64_inventec_d7032q28b
$(LIBRARY)_SUBDIR := $(dir $(lastword $(MAKEFILE_LIST)))
include $(BUILDER)/lib.mk

Some files were not shown because too many files have changed in this diff Show More