diff options
author | Amit Kumar Salecha <amit.salecha@qlogic.com> | 2010-08-16 20:34:22 -0400 |
---|---|---|
committer | David S. Miller <davem@davemloft.net> | 2010-08-17 06:59:47 -0400 |
commit | b6021212291d1eb1e7d1245bbd8c53bcbe2355d7 (patch) | |
tree | bc10d1a36a46aaa8e1646a644e77ecafa88a0f14 /drivers/net/qlcnic/qlcnic_main.c | |
parent | ecd7d31038e2e0e95b4596eec021e02ba67a0a37 (diff) |
qlcnic: add eswitch statistics support
Adding eswitch statistics support. User can get
whole eswitch stats or stats of func belong to that eswitch.
Added:
o command to get statistics of eswitch and function.
o sysfs support to export eswitch and func statatistics.
Signed-off-by: Amit Kumar Salecha <amit.salecha@qlogic.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'drivers/net/qlcnic/qlcnic_main.c')
-rw-r--r-- | drivers/net/qlcnic/qlcnic_main.c | 132 |
1 files changed, 131 insertions, 1 deletions
diff --git a/drivers/net/qlcnic/qlcnic_main.c b/drivers/net/qlcnic/qlcnic_main.c index 06ffd7637f87..a30bde52d40b 100644 --- a/drivers/net/qlcnic/qlcnic_main.c +++ b/drivers/net/qlcnic/qlcnic_main.c | |||
@@ -3378,6 +3378,115 @@ qlcnic_sysfs_read_npar_config(struct file *file, struct kobject *kobj, | |||
3378 | } | 3378 | } |
3379 | 3379 | ||
3380 | static ssize_t | 3380 | static ssize_t |
3381 | qlcnic_sysfs_get_port_stats(struct file *file, struct kobject *kobj, | ||
3382 | struct bin_attribute *attr, char *buf, loff_t offset, size_t size) | ||
3383 | { | ||
3384 | struct device *dev = container_of(kobj, struct device, kobj); | ||
3385 | struct qlcnic_adapter *adapter = dev_get_drvdata(dev); | ||
3386 | struct qlcnic_esw_statistics port_stats; | ||
3387 | int ret; | ||
3388 | |||
3389 | if (size != sizeof(struct qlcnic_esw_statistics)) | ||
3390 | return QL_STATUS_INVALID_PARAM; | ||
3391 | |||
3392 | if (offset >= QLCNIC_MAX_PCI_FUNC) | ||
3393 | return QL_STATUS_INVALID_PARAM; | ||
3394 | |||
3395 | memset(&port_stats, 0, size); | ||
3396 | ret = qlcnic_get_port_stats(adapter, offset, QLCNIC_QUERY_RX_COUNTER, | ||
3397 | &port_stats.rx); | ||
3398 | if (ret) | ||
3399 | return ret; | ||
3400 | |||
3401 | ret = qlcnic_get_port_stats(adapter, offset, QLCNIC_QUERY_TX_COUNTER, | ||
3402 | &port_stats.tx); | ||
3403 | if (ret) | ||
3404 | return ret; | ||
3405 | |||
3406 | memcpy(buf, &port_stats, size); | ||
3407 | return size; | ||
3408 | } | ||
3409 | |||
3410 | static ssize_t | ||
3411 | qlcnic_sysfs_get_esw_stats(struct file *file, struct kobject *kobj, | ||
3412 | struct bin_attribute *attr, char *buf, loff_t offset, size_t size) | ||
3413 | { | ||
3414 | struct device *dev = container_of(kobj, struct device, kobj); | ||
3415 | struct qlcnic_adapter *adapter = dev_get_drvdata(dev); | ||
3416 | struct qlcnic_esw_statistics esw_stats; | ||
3417 | int ret; | ||
3418 | |||
3419 | if (size != sizeof(struct qlcnic_esw_statistics)) | ||
3420 | return QL_STATUS_INVALID_PARAM; | ||
3421 | |||
3422 | if (offset >= QLCNIC_NIU_MAX_XG_PORTS) | ||
3423 | return QL_STATUS_INVALID_PARAM; | ||
3424 | |||
3425 | memset(&esw_stats, 0, size); | ||
3426 | ret = qlcnic_get_eswitch_stats(adapter, offset, QLCNIC_QUERY_RX_COUNTER, | ||
3427 | &esw_stats.rx); | ||
3428 | if (ret) | ||
3429 | return ret; | ||
3430 | |||
3431 | ret = qlcnic_get_eswitch_stats(adapter, offset, QLCNIC_QUERY_TX_COUNTER, | ||
3432 | &esw_stats.tx); | ||
3433 | if (ret) | ||
3434 | return ret; | ||
3435 | |||
3436 | memcpy(buf, &esw_stats, size); | ||
3437 | return size; | ||
3438 | } | ||
3439 | |||
3440 | static ssize_t | ||
3441 | qlcnic_sysfs_clear_esw_stats(struct file *file, struct kobject *kobj, | ||
3442 | struct bin_attribute *attr, char *buf, loff_t offset, size_t size) | ||
3443 | { | ||
3444 | struct device *dev = container_of(kobj, struct device, kobj); | ||
3445 | struct qlcnic_adapter *adapter = dev_get_drvdata(dev); | ||
3446 | int ret; | ||
3447 | |||
3448 | if (offset >= QLCNIC_NIU_MAX_XG_PORTS) | ||
3449 | return QL_STATUS_INVALID_PARAM; | ||
3450 | |||
3451 | ret = qlcnic_clear_esw_stats(adapter, QLCNIC_STATS_ESWITCH, offset, | ||
3452 | QLCNIC_QUERY_RX_COUNTER); | ||
3453 | if (ret) | ||
3454 | return ret; | ||
3455 | |||
3456 | ret = qlcnic_clear_esw_stats(adapter, QLCNIC_STATS_ESWITCH, offset, | ||
3457 | QLCNIC_QUERY_TX_COUNTER); | ||
3458 | if (ret) | ||
3459 | return ret; | ||
3460 | |||
3461 | return size; | ||
3462 | } | ||
3463 | |||
3464 | static ssize_t | ||
3465 | qlcnic_sysfs_clear_port_stats(struct file *file, struct kobject *kobj, | ||
3466 | struct bin_attribute *attr, char *buf, loff_t offset, size_t size) | ||
3467 | { | ||
3468 | |||
3469 | struct device *dev = container_of(kobj, struct device, kobj); | ||
3470 | struct qlcnic_adapter *adapter = dev_get_drvdata(dev); | ||
3471 | int ret; | ||
3472 | |||
3473 | if (offset >= QLCNIC_MAX_PCI_FUNC) | ||
3474 | return QL_STATUS_INVALID_PARAM; | ||
3475 | |||
3476 | ret = qlcnic_clear_esw_stats(adapter, QLCNIC_STATS_PORT, offset, | ||
3477 | QLCNIC_QUERY_RX_COUNTER); | ||
3478 | if (ret) | ||
3479 | return ret; | ||
3480 | |||
3481 | ret = qlcnic_clear_esw_stats(adapter, QLCNIC_STATS_PORT, offset, | ||
3482 | QLCNIC_QUERY_TX_COUNTER); | ||
3483 | if (ret) | ||
3484 | return ret; | ||
3485 | |||
3486 | return size; | ||
3487 | } | ||
3488 | |||
3489 | static ssize_t | ||
3381 | qlcnic_sysfs_read_pci_config(struct file *file, struct kobject *kobj, | 3490 | qlcnic_sysfs_read_pci_config(struct file *file, struct kobject *kobj, |
3382 | struct bin_attribute *attr, char *buf, loff_t offset, size_t size) | 3491 | struct bin_attribute *attr, char *buf, loff_t offset, size_t size) |
3383 | { | 3492 | { |
@@ -3426,6 +3535,20 @@ static struct bin_attribute bin_attr_pci_config = { | |||
3426 | .write = NULL, | 3535 | .write = NULL, |
3427 | }; | 3536 | }; |
3428 | 3537 | ||
3538 | static struct bin_attribute bin_attr_port_stats = { | ||
3539 | .attr = {.name = "port_stats", .mode = (S_IRUGO | S_IWUSR)}, | ||
3540 | .size = 0, | ||
3541 | .read = qlcnic_sysfs_get_port_stats, | ||
3542 | .write = qlcnic_sysfs_clear_port_stats, | ||
3543 | }; | ||
3544 | |||
3545 | static struct bin_attribute bin_attr_esw_stats = { | ||
3546 | .attr = {.name = "esw_stats", .mode = (S_IRUGO | S_IWUSR)}, | ||
3547 | .size = 0, | ||
3548 | .read = qlcnic_sysfs_get_esw_stats, | ||
3549 | .write = qlcnic_sysfs_clear_esw_stats, | ||
3550 | }; | ||
3551 | |||
3429 | static struct bin_attribute bin_attr_esw_config = { | 3552 | static struct bin_attribute bin_attr_esw_config = { |
3430 | .attr = {.name = "esw_config", .mode = (S_IRUGO | S_IWUSR)}, | 3553 | .attr = {.name = "esw_config", .mode = (S_IRUGO | S_IWUSR)}, |
3431 | .size = 0, | 3554 | .size = 0, |
@@ -3465,6 +3588,9 @@ qlcnic_create_diag_entries(struct qlcnic_adapter *adapter) | |||
3465 | { | 3588 | { |
3466 | struct device *dev = &adapter->pdev->dev; | 3589 | struct device *dev = &adapter->pdev->dev; |
3467 | 3590 | ||
3591 | if (device_create_bin_file(dev, &bin_attr_port_stats)) | ||
3592 | dev_info(dev, "failed to create port stats sysfs entry"); | ||
3593 | |||
3468 | if (adapter->op_mode == QLCNIC_NON_PRIV_FUNC) | 3594 | if (adapter->op_mode == QLCNIC_NON_PRIV_FUNC) |
3469 | return; | 3595 | return; |
3470 | if (device_create_file(dev, &dev_attr_diag_mode)) | 3596 | if (device_create_file(dev, &dev_attr_diag_mode)) |
@@ -3484,7 +3610,8 @@ qlcnic_create_diag_entries(struct qlcnic_adapter *adapter) | |||
3484 | dev_info(dev, "failed to create esw config sysfs entry"); | 3610 | dev_info(dev, "failed to create esw config sysfs entry"); |
3485 | if (device_create_bin_file(dev, &bin_attr_pm_config)) | 3611 | if (device_create_bin_file(dev, &bin_attr_pm_config)) |
3486 | dev_info(dev, "failed to create pm config sysfs entry"); | 3612 | dev_info(dev, "failed to create pm config sysfs entry"); |
3487 | 3613 | if (device_create_bin_file(dev, &bin_attr_esw_stats)) | |
3614 | dev_info(dev, "failed to create eswitch stats sysfs entry"); | ||
3488 | } | 3615 | } |
3489 | 3616 | ||
3490 | static void | 3617 | static void |
@@ -3492,6 +3619,8 @@ qlcnic_remove_diag_entries(struct qlcnic_adapter *adapter) | |||
3492 | { | 3619 | { |
3493 | struct device *dev = &adapter->pdev->dev; | 3620 | struct device *dev = &adapter->pdev->dev; |
3494 | 3621 | ||
3622 | device_remove_bin_file(dev, &bin_attr_port_stats); | ||
3623 | |||
3495 | if (adapter->op_mode == QLCNIC_NON_PRIV_FUNC) | 3624 | if (adapter->op_mode == QLCNIC_NON_PRIV_FUNC) |
3496 | return; | 3625 | return; |
3497 | device_remove_file(dev, &dev_attr_diag_mode); | 3626 | device_remove_file(dev, &dev_attr_diag_mode); |
@@ -3504,6 +3633,7 @@ qlcnic_remove_diag_entries(struct qlcnic_adapter *adapter) | |||
3504 | device_remove_bin_file(dev, &bin_attr_npar_config); | 3633 | device_remove_bin_file(dev, &bin_attr_npar_config); |
3505 | device_remove_bin_file(dev, &bin_attr_esw_config); | 3634 | device_remove_bin_file(dev, &bin_attr_esw_config); |
3506 | device_remove_bin_file(dev, &bin_attr_pm_config); | 3635 | device_remove_bin_file(dev, &bin_attr_pm_config); |
3636 | device_remove_bin_file(dev, &bin_attr_esw_stats); | ||
3507 | } | 3637 | } |
3508 | 3638 | ||
3509 | #ifdef CONFIG_INET | 3639 | #ifdef CONFIG_INET |