mlxreg_lc
mlxreg_lc_create_static_devices(struct mlxreg_lc *mlxreg_lc, struct mlxreg_hotplug_device *devs,
dev_err(mlxreg_lc->dev, "Failed to create client %s at bus %d at addr 0x%02x\n",
mlxreg_lc_destroy_static_devices(struct mlxreg_lc *mlxreg_lc, struct mlxreg_hotplug_device *devs,
static int mlxreg_lc_power_on_off(struct mlxreg_lc *mlxreg_lc, u8 action)
err = regmap_read(mlxreg_lc->par_regmap, mlxreg_lc->data->reg_pwr, ®val);
regval |= BIT(mlxreg_lc->data->slot - 1);
regval &= ~BIT(mlxreg_lc->data->slot - 1);
err = regmap_write(mlxreg_lc->par_regmap, mlxreg_lc->data->reg_pwr, regval);
static int mlxreg_lc_enable_disable(struct mlxreg_lc *mlxreg_lc, bool action)
err = regmap_read(mlxreg_lc->par_regmap, mlxreg_lc->data->reg_ena, ®val);
regval |= BIT(mlxreg_lc->data->slot - 1);
regval &= ~BIT(mlxreg_lc->data->slot - 1);
err = regmap_write(mlxreg_lc->par_regmap, mlxreg_lc->data->reg_ena, regval);
mlxreg_lc_sn4800_c16_config_init(struct mlxreg_lc *mlxreg_lc, void *regmap,
mlxreg_lc->mux_data = mlxreg_lc_mux_data;
mlxreg_lc->io_data = &mlxreg_lc_regs_io;
mlxreg_lc->led_data = &mlxreg_lc_led;
mlxreg_lc->mux_brdinfo = &mlxreg_lc_mux_brdinfo;
mlxreg_lc->aux_devs = devm_kmemdup(dev, mlxreg_lc_aux_pwr_brdinfo,
if (!mlxreg_lc->aux_devs)
mlxreg_lc->aux_devs_num = ARRAY_SIZE(mlxreg_lc_aux_pwr_brdinfo);
mlxreg_lc->main_devs = devm_kmemdup(dev, mlxreg_lc_main_pwr_brdinfo,
if (!mlxreg_lc->main_devs)
mlxreg_lc->main_devs_num = ARRAY_SIZE(mlxreg_lc_main_pwr_brdinfo);
mlxreg_lc_state_update(struct mlxreg_lc *mlxreg_lc, enum mlxreg_lc_state state, u8 action)
mlxreg_lc->state |= state;
mlxreg_lc->state &= ~state;
mlxreg_lc_state_update_locked(struct mlxreg_lc *mlxreg_lc, enum mlxreg_lc_state state, u8 action)
mutex_lock(&mlxreg_lc->lock);
mlxreg_lc->state |= state;
mlxreg_lc->state &= ~state;
mutex_unlock(&mlxreg_lc->lock);
struct mlxreg_lc *mlxreg_lc = handle;
dev_info(mlxreg_lc->dev, "linecard#%d state %d event kind %d action %d\n",
mlxreg_lc->data->slot, mlxreg_lc->state, kind, action);
mutex_lock(&mlxreg_lc->lock);
if (!(mlxreg_lc->state & MLXREG_LC_INITIALIZED))
mlxreg_lc_state_update(mlxreg_lc, MLXREG_LC_SYNCED, action);
if (!(mlxreg_lc->state & MLXREG_LC_POWERED) && action) {
err = mlxreg_lc_power_on_off(mlxreg_lc, 1);
if (mlxreg_lc->state & MLXREG_LC_CONFIGURED && action)
err = mlxreg_lc_enable_disable(mlxreg_lc, 1);
if (mlxreg_lc->state & MLXREG_LC_POWERED) {
if (mlxreg_lc->state & MLXREG_LC_CONFIGURED)
err = mlxreg_lc_enable_disable(mlxreg_lc, 1);
err = mlxreg_lc_create_static_devices(mlxreg_lc, mlxreg_lc->main_devs,
mlxreg_lc->main_devs_num);
if (mlxreg_lc->state & MLXREG_LC_CONFIGURED)
err = mlxreg_lc_enable_disable(mlxreg_lc, 1);
mlxreg_lc_destroy_static_devices(mlxreg_lc, mlxreg_lc->main_devs,
mlxreg_lc->main_devs_num);
mlxreg_lc_state_update(mlxreg_lc, MLXREG_LC_POWERED, action);
err = mlxreg_lc_enable_disable(mlxreg_lc, !!action);
err = mlxreg_lc_power_on_off(mlxreg_lc, 0);
mutex_unlock(&mlxreg_lc->lock);
struct mlxreg_lc *mlxreg_lc = handle;
aux_dev = mlxreg_lc->aux_devs;
for (i = 0; i < mlxreg_lc->aux_devs_num; i++, aux_dev++) {
err = mlxreg_lc_create_static_devices(mlxreg_lc, mlxreg_lc->aux_devs,
mlxreg_lc->aux_devs_num);
main_dev = mlxreg_lc->main_devs;
for (i = 0; i < mlxreg_lc->main_devs_num; i++, main_dev++) {
err = regmap_read(mlxreg_lc->par_regmap, mlxreg_lc->data->reg_pwr, ®val);
if (regval & mlxreg_lc->data->mask) {
err = mlxreg_lc_create_static_devices(mlxreg_lc, mlxreg_lc->main_devs,
mlxreg_lc->main_devs_num);
mlxreg_lc_state_update_locked(mlxreg_lc, MLXREG_LC_POWERED, 1);
err = regmap_read(mlxreg_lc->par_regmap, mlxreg_lc->data->reg_sync, ®val);
if (regval & mlxreg_lc->data->mask) {
mlxreg_lc->state |= MLXREG_LC_SYNCED;
mlxreg_lc_state_update_locked(mlxreg_lc, MLXREG_LC_SYNCED, 1);
if (!(mlxreg_lc->state & MLXREG_LC_POWERED)) {
err = mlxreg_lc_power_on_off(mlxreg_lc, 1);
mlxreg_lc_state_update_locked(mlxreg_lc, MLXREG_LC_INITIALIZED, 1);
if (mlxreg_lc->state & MLXREG_LC_POWERED)
mlxreg_lc_destroy_static_devices(mlxreg_lc, mlxreg_lc->main_devs,
mlxreg_lc->main_devs_num);
mlxreg_lc_destroy_static_devices(mlxreg_lc, mlxreg_lc->aux_devs, mlxreg_lc->aux_devs_num);
mlxreg_lc_config_init(struct mlxreg_lc *mlxreg_lc, void *regmap,
err = mlxreg_lc_sn4800_c16_config_init(mlxreg_lc, regmap, data);
mlxreg_lc->mux_data->handle = mlxreg_lc;
mlxreg_lc->mux_data->completion_notify = mlxreg_lc_completion_notify;
mlxreg_lc->mux_brdinfo->platform_data = mlxreg_lc->mux_data;
mlxreg_lc->mux = platform_device_register_resndata(dev, "i2c-mux-mlxcpld", data->hpdev.nr,
NULL, 0, mlxreg_lc->mux_data,
sizeof(*mlxreg_lc->mux_data));
if (IS_ERR(mlxreg_lc->mux)) {
return PTR_ERR(mlxreg_lc->mux);
if (mlxreg_lc->io_data) {
mlxreg_lc->io_data->regmap = regmap;
mlxreg_lc->io_regs =
mlxreg_lc->io_data, sizeof(*mlxreg_lc->io_data));
if (IS_ERR(mlxreg_lc->io_regs)) {
err = PTR_ERR(mlxreg_lc->io_regs);
if (mlxreg_lc->led_data) {
mlxreg_lc->led_data->regmap = regmap;
mlxreg_lc->led =
mlxreg_lc->led_data,
sizeof(*mlxreg_lc->led_data));
if (IS_ERR(mlxreg_lc->led)) {
err = PTR_ERR(mlxreg_lc->led);
if (mlxreg_lc->io_regs)
platform_device_unregister(mlxreg_lc->io_regs);
if (mlxreg_lc->mux)
platform_device_unregister(mlxreg_lc->mux);
static void mlxreg_lc_config_exit(struct mlxreg_lc *mlxreg_lc)
if (mlxreg_lc->led)
platform_device_unregister(mlxreg_lc->led);
if (mlxreg_lc->io_regs)
platform_device_unregister(mlxreg_lc->io_regs);
if (mlxreg_lc->mux)
platform_device_unregister(mlxreg_lc->mux);
struct mlxreg_lc *mlxreg_lc;
mlxreg_lc = devm_kzalloc(&pdev->dev, sizeof(*mlxreg_lc), GFP_KERNEL);
if (!mlxreg_lc)
mutex_init(&mlxreg_lc->lock);
data->notifier->handle = mlxreg_lc;
mlxreg_lc->par_regmap = par_pdata->regmap;
mlxreg_lc->data = data;
mlxreg_lc->dev = &pdev->dev;
platform_set_drvdata(pdev, mlxreg_lc);
err = mlxreg_lc_config_init(mlxreg_lc, regmap, data);
struct mlxreg_lc *mlxreg_lc = platform_get_drvdata(pdev);
mlxreg_lc_state_update_locked(mlxreg_lc, MLXREG_LC_INITIALIZED, 0);
mlxreg_lc_destroy_static_devices(mlxreg_lc, mlxreg_lc->main_devs,
mlxreg_lc->main_devs_num);
mlxreg_lc_destroy_static_devices(mlxreg_lc, mlxreg_lc->aux_devs, mlxreg_lc->aux_devs_num);
mlxreg_lc_config_exit(mlxreg_lc);