mirror of
				https://github.com/Telecominfraproject/OpenNetworkLinux.git
				synced 2025-11-03 19:58:20 +00:00 
			
		
		
		
	[as5916-54xks] Add support for YM-2851J DC PSU
This commit is contained in:
		@@ -39,6 +39,7 @@
 | 
			
		||||
 | 
			
		||||
static void ipmi_msg_handler(struct ipmi_recv_msg *msg, void *user_msg_data);
 | 
			
		||||
static ssize_t show_linear(struct device *dev, struct device_attribute *attr, char *buf);
 | 
			
		||||
static ssize_t show_vout(struct device *dev, struct device_attribute *da, char *buf);
 | 
			
		||||
static ssize_t show_psu(struct device *dev, struct device_attribute *attr, char *buf);
 | 
			
		||||
static ssize_t show_string(struct device *dev, struct device_attribute *attr, char *buf);
 | 
			
		||||
static int as5916_54xks_psu_probe(struct platform_device *pdev);
 | 
			
		||||
@@ -70,6 +71,7 @@ enum psu_data_index {
 | 
			
		||||
    PSU_FAN1,
 | 
			
		||||
    PSU_POUT0,
 | 
			
		||||
    PSU_POUT1,
 | 
			
		||||
    PSU_VOUT_MODE,
 | 
			
		||||
    PSU_STATUS_COUNT,
 | 
			
		||||
    PSU_MODEL = 0,
 | 
			
		||||
    PSU_SERIAL = 0
 | 
			
		||||
@@ -93,7 +95,7 @@ struct ipmi_data {
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
struct ipmi_psu_resp_data {
 | 
			
		||||
    unsigned char   status[19];
 | 
			
		||||
    unsigned char   status[20];
 | 
			
		||||
    char   serial[19];
 | 
			
		||||
    char   model[9];
 | 
			
		||||
};
 | 
			
		||||
@@ -152,7 +154,7 @@ enum as5916_54x_psu_sysfs_attrs {
 | 
			
		||||
#define DECLARE_PSU_SENSOR_DEVICE_ATTR(index) \
 | 
			
		||||
	static SENSOR_DEVICE_ATTR(psu##index##_present,    S_IRUGO, show_psu, NULL, PSU##index##_PRESENT); \
 | 
			
		||||
	static SENSOR_DEVICE_ATTR(psu##index##_power_good, S_IRUGO, show_psu, NULL, PSU##index##_POWER_GOOD); \
 | 
			
		||||
	static SENSOR_DEVICE_ATTR(psu##index##_vout, S_IRUGO, show_linear,  NULL, PSU##index##_VOUT); \
 | 
			
		||||
	static SENSOR_DEVICE_ATTR(psu##index##_vout, S_IRUGO, show_vout,  NULL, PSU##index##_VOUT); \
 | 
			
		||||
	static SENSOR_DEVICE_ATTR(psu##index##_iout, S_IRUGO, show_linear,  NULL, PSU##index##_IOUT); \
 | 
			
		||||
	static SENSOR_DEVICE_ATTR(psu##index##_pout, S_IRUGO, show_linear,  NULL, PSU##index##_POUT); \
 | 
			
		||||
	static SENSOR_DEVICE_ATTR(psu##index##_model, S_IRUGO, show_string,  NULL, PSU##index##_MODEL); \
 | 
			
		||||
@@ -304,6 +306,7 @@ static struct as5916_54xks_psu_data *as5916_54xks_psu_update_device(struct devic
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    data->valid[pid] = 0;
 | 
			
		||||
    data->ipmi_resp[pid].status[PSU_VOUT_MODE] = 0xff; /* To be compatible for older BMC firmware */
 | 
			
		||||
 | 
			
		||||
    /* Get status from ipmi */
 | 
			
		||||
    data->ipmi_tx_data[0] = pid + 1; /* PSU ID base id for ipmi start from 1 */
 | 
			
		||||
@@ -319,7 +322,7 @@ static struct as5916_54xks_psu_data *as5916_54xks_psu_update_device(struct devic
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /* Get model name from ipmi */
 | 
			
		||||
    data->ipmi_tx_data[1] = 0x10;
 | 
			
		||||
    data->ipmi_tx_data[1] = IPMI_PSU_MODEL_NAME_CMD;
 | 
			
		||||
    status = ipmi_send_message(&data->ipmi, IPMI_PSU_READ_CMD, data->ipmi_tx_data, 2,
 | 
			
		||||
                                data->ipmi_resp[pid].model, sizeof(data->ipmi_resp[pid].model) - 1);
 | 
			
		||||
    if (unlikely(status != 0)) {
 | 
			
		||||
@@ -332,7 +335,7 @@ static struct as5916_54xks_psu_data *as5916_54xks_psu_update_device(struct devic
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /* Get serial number from ipmi */
 | 
			
		||||
    data->ipmi_tx_data[1] = 0x11;
 | 
			
		||||
    data->ipmi_tx_data[1] = IPMI_PSU_SERIAL_NUM_CMD;
 | 
			
		||||
    status = ipmi_send_message(&data->ipmi, IPMI_PSU_READ_CMD,  data->ipmi_tx_data, 2,
 | 
			
		||||
                                data->ipmi_resp[pid].serial, sizeof(data->ipmi_resp[pid].serial) - 1);
 | 
			
		||||
    if (unlikely(status != 0)) {
 | 
			
		||||
@@ -421,6 +424,50 @@ exit:
 | 
			
		||||
    return error;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static ssize_t show_vout(struct device *dev, struct device_attribute *da, char *buf)
 | 
			
		||||
{
 | 
			
		||||
    struct sensor_device_attribute *attr = to_sensor_dev_attr(da);
 | 
			
		||||
    unsigned char pid = attr->index / NUM_OF_PER_PSU_ATTR;
 | 
			
		||||
    u16 value = 0;
 | 
			
		||||
    int error = 0;
 | 
			
		||||
	int exponent = 0, mantissa = 0;
 | 
			
		||||
	int multiplier = 1000;
 | 
			
		||||
    u8  vout_mode = 0xff;    
 | 
			
		||||
 | 
			
		||||
    mutex_lock(&data->update_lock);
 | 
			
		||||
 | 
			
		||||
    data = as5916_54xks_psu_update_device(da);
 | 
			
		||||
    if (!data->valid[pid]) {
 | 
			
		||||
        error = -EIO;
 | 
			
		||||
        goto exit;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    vout_mode = (u8)data->ipmi_resp[pid].status[PSU_VOUT_MODE];
 | 
			
		||||
	value     = ((u16)data->ipmi_resp[pid].status[PSU_VOUT0] |
 | 
			
		||||
                 (u16)data->ipmi_resp[pid].status[PSU_VOUT1] << 8);
 | 
			
		||||
 | 
			
		||||
    mutex_unlock(&data->update_lock);
 | 
			
		||||
 | 
			
		||||
    if (vout_mode == 0xff) {
 | 
			
		||||
        exponent = two_complement_to_int(value >> 11, 5, 0x1f);
 | 
			
		||||
        mantissa = two_complement_to_int(value & 0x7ff, 11, 0x7ff);
 | 
			
		||||
    }
 | 
			
		||||
    else if (!(vout_mode & 0xe0)){
 | 
			
		||||
        exponent = two_complement_to_int(vout_mode & 0x1f, 5, 0x1f);
 | 
			
		||||
        mantissa = two_complement_to_int(value & 0xffff, 16, 0xffff);
 | 
			
		||||
    }
 | 
			
		||||
    else {
 | 
			
		||||
        return -EINVAL;
 | 
			
		||||
    }    
 | 
			
		||||
 | 
			
		||||
	return (exponent >= 0) ? sprintf(buf, "%d\n", (mantissa << exponent) * multiplier) :
 | 
			
		||||
							 sprintf(buf, "%d\n", (mantissa * multiplier) / (1 << -exponent));
 | 
			
		||||
 | 
			
		||||
exit:
 | 
			
		||||
    mutex_unlock(&data->update_lock);
 | 
			
		||||
    return error;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static ssize_t show_psu(struct device *dev, struct device_attribute *da, char *buf)
 | 
			
		||||
{
 | 
			
		||||
    struct sensor_device_attribute *attr = to_sensor_dev_attr(da);
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user