namespace_devs.c 2.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111
  1. /*
  2. * Copyright(c) 2013-2015 Intel Corporation. All rights reserved.
  3. *
  4. * This program is free software; you can redistribute it and/or modify
  5. * it under the terms of version 2 of the GNU General Public License as
  6. * published by the Free Software Foundation.
  7. *
  8. * This program is distributed in the hope that it will be useful, but
  9. * WITHOUT ANY WARRANTY; without even the implied warranty of
  10. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
  11. * General Public License for more details.
  12. */
  13. #include <linux/module.h>
  14. #include <linux/device.h>
  15. #include <linux/slab.h>
  16. #include <linux/nd.h>
  17. #include "nd.h"
  18. static void namespace_io_release(struct device *dev)
  19. {
  20. struct nd_namespace_io *nsio = to_nd_namespace_io(dev);
  21. kfree(nsio);
  22. }
  23. static struct device_type namespace_io_device_type = {
  24. .name = "nd_namespace_io",
  25. .release = namespace_io_release,
  26. };
  27. static ssize_t nstype_show(struct device *dev,
  28. struct device_attribute *attr, char *buf)
  29. {
  30. struct nd_region *nd_region = to_nd_region(dev->parent);
  31. return sprintf(buf, "%d\n", nd_region_to_nstype(nd_region));
  32. }
  33. static DEVICE_ATTR_RO(nstype);
  34. static struct attribute *nd_namespace_attributes[] = {
  35. &dev_attr_nstype.attr,
  36. NULL,
  37. };
  38. static struct attribute_group nd_namespace_attribute_group = {
  39. .attrs = nd_namespace_attributes,
  40. };
  41. static const struct attribute_group *nd_namespace_attribute_groups[] = {
  42. &nd_device_attribute_group,
  43. &nd_namespace_attribute_group,
  44. NULL,
  45. };
  46. static struct device **create_namespace_io(struct nd_region *nd_region)
  47. {
  48. struct nd_namespace_io *nsio;
  49. struct device *dev, **devs;
  50. struct resource *res;
  51. nsio = kzalloc(sizeof(*nsio), GFP_KERNEL);
  52. if (!nsio)
  53. return NULL;
  54. devs = kcalloc(2, sizeof(struct device *), GFP_KERNEL);
  55. if (!devs) {
  56. kfree(nsio);
  57. return NULL;
  58. }
  59. dev = &nsio->dev;
  60. dev->type = &namespace_io_device_type;
  61. dev->parent = &nd_region->dev;
  62. res = &nsio->res;
  63. res->name = dev_name(&nd_region->dev);
  64. res->flags = IORESOURCE_MEM;
  65. res->start = nd_region->ndr_start;
  66. res->end = res->start + nd_region->ndr_size - 1;
  67. devs[0] = dev;
  68. return devs;
  69. }
  70. int nd_region_register_namespaces(struct nd_region *nd_region, int *err)
  71. {
  72. struct device **devs = NULL;
  73. int i;
  74. *err = 0;
  75. switch (nd_region_to_nstype(nd_region)) {
  76. case ND_DEVICE_NAMESPACE_IO:
  77. devs = create_namespace_io(nd_region);
  78. break;
  79. default:
  80. break;
  81. }
  82. if (!devs)
  83. return -ENODEV;
  84. for (i = 0; devs[i]; i++) {
  85. struct device *dev = devs[i];
  86. dev_set_name(dev, "namespace%d.%d", nd_region->id, i);
  87. dev->groups = nd_namespace_attribute_groups;
  88. nd_device_register(dev);
  89. }
  90. kfree(devs);
  91. return i;
  92. }