ibft: Expose iBFT acpi header via sysfs

Some ethernet adapter vendors are supplying products which support optional
(payed license) features. On some adapters this includes a hardware iscsi
initiator.  The same adapters in a normal (no extra licenses) mode of
operation can be used as a software iscsi initiator.  In addition, software
iscsi boot initiators are becoming a standard part of many vendors uefi
implementations.  This is creating difficulties during early boot/install
determining the proper configuration method for these adapters when they
are used as a boot device.

The attached patch creates sysfs entries to expose information from the
acpi header of the ibft table.  This information allows for a method to
easily determining if an ibft table was created by a ethernet card's
firmware or the system uefi/bios.  In the case of a hardware initiator this
information in combination with the pci vendor and device id can be used
to ascertain any vendor specific behaviors that need to be accommodated.

Reviewed-by: Lee Duncan <lduncan@suse.com>
Signed-off-by: David Bond <dbond@suse.com>
Signed-off-by: Konrad Rzeszutek Wilk <konrad.wilk@oracle.com>
This commit is contained in:
David Bond
2016-03-23 21:49:26 -04:00
committed by Konrad Rzeszutek Wilk
parent 9a99425f07
commit b3c8eb5038
4 changed files with 150 additions and 1 deletions

View File

@@ -306,6 +306,42 @@ static struct attribute_group iscsi_boot_initiator_attr_group = {
.is_visible = iscsi_boot_ini_attr_is_visible,
};
/* iBFT ACPI Table attributes */
iscsi_boot_rd_attr(acpitbl_signature, signature, ISCSI_BOOT_ACPITBL_SIGNATURE);
iscsi_boot_rd_attr(acpitbl_oem_id, oem_id, ISCSI_BOOT_ACPITBL_OEM_ID);
iscsi_boot_rd_attr(acpitbl_oem_table_id, oem_table_id,
ISCSI_BOOT_ACPITBL_OEM_TABLE_ID);
static struct attribute *acpitbl_attrs[] = {
&iscsi_boot_attr_acpitbl_signature.attr,
&iscsi_boot_attr_acpitbl_oem_id.attr,
&iscsi_boot_attr_acpitbl_oem_table_id.attr,
NULL
};
static umode_t iscsi_boot_acpitbl_attr_is_visible(struct kobject *kobj,
struct attribute *attr, int i)
{
struct iscsi_boot_kobj *boot_kobj =
container_of(kobj, struct iscsi_boot_kobj, kobj);
if (attr == &iscsi_boot_attr_acpitbl_signature.attr)
return boot_kobj->is_visible(boot_kobj->data,
ISCSI_BOOT_ACPITBL_SIGNATURE);
if (attr == &iscsi_boot_attr_acpitbl_oem_id.attr)
return boot_kobj->is_visible(boot_kobj->data,
ISCSI_BOOT_ACPITBL_OEM_ID);
if (attr == &iscsi_boot_attr_acpitbl_oem_table_id.attr)
return boot_kobj->is_visible(boot_kobj->data,
ISCSI_BOOT_ACPITBL_OEM_TABLE_ID);
return 0;
}
static struct attribute_group iscsi_boot_acpitbl_attr_group = {
.attrs = acpitbl_attrs,
.is_visible = iscsi_boot_acpitbl_attr_is_visible,
};
static struct iscsi_boot_kobj *
iscsi_boot_create_kobj(struct iscsi_boot_kset *boot_kset,
struct attribute_group *attr_group,
@@ -435,6 +471,32 @@ iscsi_boot_create_ethernet(struct iscsi_boot_kset *boot_kset, int index,
}
EXPORT_SYMBOL_GPL(iscsi_boot_create_ethernet);
/**
* iscsi_boot_create_acpitbl() - create boot acpi table sysfs dir
* @boot_kset: boot kset
* @index: not used
* @data: driver specific data
* @show: attr show function
* @is_visible: attr visibility function
* @release: release function
*
* Note: The boot sysfs lib will free the data passed in for the caller
* when all refs to the acpitbl kobject have been released.
*/
struct iscsi_boot_kobj *
iscsi_boot_create_acpitbl(struct iscsi_boot_kset *boot_kset, int index,
void *data,
ssize_t (*show)(void *data, int type, char *buf),
umode_t (*is_visible)(void *data, int type),
void (*release)(void *data))
{
return iscsi_boot_create_kobj(boot_kset,
&iscsi_boot_acpitbl_attr_group,
"acpi_header", index, data, show,
is_visible, release);
}
EXPORT_SYMBOL_GPL(iscsi_boot_create_acpitbl);
/**
* iscsi_boot_create_kset() - creates root sysfs tree
* @set_name: name of root dir