* [RFC PATCH 8/19] Target_Core_Mod Subsystem and SE Object plugin infrastructure
@ 2009-09-18 22:08 Nicholas A. Bellinger
0 siblings, 0 replies; 2+ messages in thread
From: Nicholas A. Bellinger @ 2009-09-18 22:08 UTC (permalink / raw)
To: LKML, linux-scsi
Cc: Andrew Morton, Greg KH, Douglas Gilbert, James Bottomley,
Hannes Reinecke, FUJITA Tomonori, Mike Christie, Joel Becker,
Martin K. Petersen, Christoph Hellwig, Linus Torvalds,
Alan Stern, Boaz Harrosh, Florian Haas, Philipp Reisner,
Lars Ellenberg, Daniel Walker
[RFC PATCH 8/19] Target_Core_Mod Subsystem and SE Object plugin infrastructure
This patch adds the simple plugin infrastructure used by subsystem and seobj plugins.
Signed-off-by: Nicholas A. Bellinger <nab@linux-iscsi.org>
diff --git a/drivers/target/target_core_plugin.c b/drivers/target/target_core_plugin.c
new file mode 100644
index 0000000..9f7ea97
--- /dev/null
+++ b/drivers/target/target_core_plugin.c
@@ -0,0 +1,326 @@
+/*******************************************************************************
+ * Filename: target_core_plugin.c
+ *
+ * Copyright (c) 2006-2007 SBE, Inc. All Rights Reserved.
+ * Copyright (c) 2007-2009 Rising Tide Software, Inc.
+ * Copyright (c) 2008-2009 Linux-iSCSI.org
+ *
+ * Nicholas A. Bellinger <nab@kernel.org>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
+ *
+ ******************************************************************************/
+
+#define TARGET_CORE_PLUGIN_C
+
+#include <linux/net.h>
+#include <linux/string.h>
+#include <linux/timer.h>
+#include <linux/slab.h>
+#include <linux/spinlock.h>
+#include <linux/smp_lock.h>
+#include <linux/in.h>
+#include <net/sock.h>
+#include <net/tcp.h>
+
+#include <target/target_core_base.h>
+#include <target/target_core_hba.h>
+#include <target/target_core_seobj.h>
+#include <target/target_core_transport.h>
+#include <target/target_core_plugin.h>
+
+#undef TARGET_CORE_PLUGIN_C
+
+void plugin_load_all_classes(void)
+{
+ /*
+ * Setup Transport Plugins
+ */
+ plugin_register_class(PLUGIN_TYPE_TRANSPORT, "TRANSPORT", MAX_PLUGINS);
+ transport_load_plugins();
+
+ /*
+ * Setup Storage Engine Object Plugins
+ */
+ plugin_register_class(PLUGIN_TYPE_OBJ, "OBJ", MAX_PLUGINS);
+ se_obj_load_plugins();
+}
+EXPORT_SYMBOL(plugin_load_all_classes);
+
+se_plugin_class_t *plugin_get_class(
+ u32 plugin_class_type)
+{
+ se_plugin_class_t *pc;
+
+ if (plugin_class_type > MAX_PLUGIN_CLASSES) {
+ printk(KERN_ERR "Passed plugin class type: %u exceeds"
+ " MAX_PLUGIN_CLASSES: %d\n", plugin_class_type,
+ MAX_PLUGIN_CLASSES);
+ return NULL;
+ }
+
+ pc = &se_global->plugin_class_list[plugin_class_type];
+ if (!pc->plugin_array)
+ return NULL;
+
+ return pc;
+}
+
+int plugin_register_class(
+ u32 plugin_class_type,
+ unsigned char *plugin_class_name,
+ int max_plugins)
+{
+ u32 i;
+ se_plugin_class_t *pc;
+ se_plugin_t *p;
+
+ if (strlen(plugin_class_name) > MAX_PLUGIN_CLASS_NAME) {
+ printk(KERN_ERR "plugin_class_name exceeds MAX_PLUGIN_CLASS"
+ "_NAME: %u\n", MAX_PLUGIN_CLASS_NAME);
+ return -1;
+ }
+ spin_lock(&se_global->plugin_class_lock);
+ if (plugin_class_type > MAX_PLUGIN_CLASSES) {
+ printk(KERN_ERR "Passed plugin class type: %u exceeds"
+ " MAX_PLUGIN_CLASSES: %d\n", plugin_class_type,
+ MAX_PLUGIN_CLASSES);
+ return -1;
+ }
+
+ pc = &se_global->plugin_class_list[plugin_class_type];
+ if (pc->plugin_array) {
+ printk(KERN_ERR "Plugin Class Type: %u already exists\n",
+ plugin_class_type);
+ return -1;
+ }
+ spin_unlock(&se_global->plugin_class_lock);
+
+ pc->plugin_array = kzalloc(sizeof(se_plugin_t) * max_plugins,
+ GFP_KERNEL);
+ if (!(pc->plugin_array)) {
+ printk(KERN_ERR "Unable to locate pc->plugin_array\n");
+ return -1;
+ }
+
+ spin_lock_init(&pc->plugin_lock);
+ pc->max_plugins = max_plugins;
+ pc->plugin_class = plugin_class_type;
+ snprintf(pc->plugin_class_name, MAX_PLUGIN_CLASS_NAME,
+ "%s", plugin_class_name);
+
+ for (i = 0; i < max_plugins; i++) {
+ p = &pc->plugin_array[i];
+ p->plugin_class = pc;
+ }
+
+ printk(KERN_INFO "SE_PC[%u] - Registered Plugin Class: %s\n",
+ pc->plugin_class, pc->plugin_class_name);
+
+ return 0;
+}
+EXPORT_SYMBOL(plugin_register_class);
+
+int plugin_deregister_class(u32 plugin_class_type)
+{
+ int i;
+ se_plugin_class_t *pc;
+ se_plugin_t *p;
+
+ pc = plugin_get_class(plugin_class_type);
+ if (!(pc))
+ return -1;
+
+ for (i = 0; i < MAX_PLUGINS; i++) {
+ p = &pc->plugin_array[i];
+
+ if (!p->plugin_obj)
+ continue;
+
+ plugin_deregister(i, plugin_class_type);
+ }
+
+ kfree(pc->plugin_array);
+ pc->plugin_array = NULL;
+
+ return 0;
+}
+EXPORT_SYMBOL(plugin_deregister_class);
+
+void plugin_unload_all_classes(void)
+{
+ u32 i;
+ se_plugin_class_t *pc;
+
+ for (i = 0; i < MAX_PLUGIN_CLASSES; i++) {
+ pc = &se_global->plugin_class_list[i];
+
+ if (!pc->plugin_array)
+ continue;
+
+ plugin_deregister_class(i);
+ }
+
+ return;
+}
+EXPORT_SYMBOL(plugin_unload_all_classes);
+
+void *plugin_get_obj(
+ u32 plugin_class,
+ u32 plugin_loc,
+ int *ret)
+{
+ se_plugin_class_t *pc;
+ se_plugin_t *p;
+
+ pc = plugin_get_class(plugin_class);
+ if (!(pc))
+ return NULL;
+
+ spin_lock(&pc->plugin_lock);
+ if (plugin_loc > pc->max_plugins) {
+ printk(KERN_ERR "Passed plugin_loc: %d exceeds"
+ " pc->max_plugins: %d\n", plugin_loc, pc->max_plugins);
+ goto out;
+ }
+
+ p = &pc->plugin_array[plugin_loc];
+ if (!p->plugin_obj) {
+ printk(KERN_ERR "Passed plugin_loc: %u does not exist!\n",
+ plugin_loc);
+ goto out;
+ }
+ spin_unlock(&pc->plugin_lock);
+
+ *ret = 0;
+ return p->plugin_obj;
+out:
+ *ret = -1;
+ spin_unlock(&pc->plugin_lock);
+ return NULL;
+}
+EXPORT_SYMBOL(plugin_get_obj);
+
+struct se_plugin_s *plugin_register(
+ void *obj,
+ u32 plugin_loc,
+ unsigned char *plugin_name,
+ u32 plugin_class,
+ void (*get_plugin_info)(void *, char *, int *),
+ int (*plugin_init)(void),
+ void (*plugin_free)(void),
+ int *ret)
+{
+ se_plugin_class_t *pc;
+ se_plugin_t *p;
+ int err;
+
+ if (!obj) {
+ printk(KERN_ERR "obj or plugin_class pointers are NULL!\n");
+ return NULL;
+ }
+
+ if (strlen(plugin_name) > MAX_PLUGIN_NAME) {
+ printk(KERN_ERR "plugin_name exceeds MAX_PLUGIN_NAME: %u\n",
+ MAX_PLUGIN_NAME);
+ return NULL;
+ }
+
+ pc = plugin_get_class(plugin_class);
+ if (!(pc))
+ return NULL;
+
+ spin_lock(&pc->plugin_lock);
+ if (plugin_loc > pc->max_plugins) {
+ printk(KERN_ERR "Passed plugin_loc: %u exceeds pc->max_plugins:"
+ " %d\n", plugin_loc, pc->max_plugins);
+ *ret = -1;
+ goto out;
+ }
+
+ p = &pc->plugin_array[plugin_loc];
+ if (p->plugin_obj) {
+ printk(KERN_ERR "Passed plugin_loc: %u already registered\n",
+ plugin_loc);
+ *ret = -1;
+ goto out;
+ }
+
+ p->plugin_obj = obj;
+ p->get_plugin_info = get_plugin_info;
+ p->plugin_free = plugin_free;
+ p->plugin_state = PLUGIN_REGISTERED;
+ p->plugin_type = plugin_loc;
+ snprintf(p->plugin_name, MAX_PLUGIN_NAME, "%s", plugin_name);
+
+ printk(KERN_INFO "PLUGIN_%s[%u] - %s registered\n",
+ pc->plugin_class_name, plugin_loc, plugin_name);
+ spin_unlock(&pc->plugin_lock);
+
+ if (*plugin_init != NULL) {
+ err = (*plugin_init)();
+ if (err) {
+ plugin_deregister(plugin_loc, plugin_class);
+ return NULL;
+ }
+ }
+
+ return p;
+
+out:
+ spin_unlock(&pc->plugin_lock);
+ return NULL;
+}
+EXPORT_SYMBOL(plugin_register);
+
+int plugin_deregister(
+ u32 plugin_loc,
+ u32 plugin_class)
+{
+ int ret = 0;
+ se_plugin_class_t *pc;
+ se_plugin_t *p;
+
+ pc = plugin_get_class(plugin_class);
+ if (!(pc))
+ return -1;
+
+ spin_lock(&pc->plugin_lock);
+ if (plugin_loc > pc->max_plugins) {
+ printk(KERN_ERR "Passed plugin_loc: %u exceeds pc->max_plugins:"
+ " %d\n", plugin_loc, pc->max_plugins);
+ ret = -1;
+ goto out;
+ }
+
+ p = &pc->plugin_array[plugin_loc];
+ if (!p->plugin_obj) {
+ printk(KERN_ERR "Passed plugin_loc: %u not active!\n",
+ plugin_loc);
+ ret = -1;
+ goto out;
+ }
+ spin_unlock(&pc->plugin_lock);
+
+ if (p->plugin_free)
+ p->plugin_free();
+
+ spin_lock(&pc->plugin_lock);
+ p->plugin_obj = NULL;
+ p->plugin_state = PLUGIN_FREE;
+out:
+ spin_unlock(&pc->plugin_lock);
+ return ret;
+}
diff --git a/include/target/target_core_plugin.h b/include/target/target_core_plugin.h
new file mode 100644
index 0000000..bc3333b
--- /dev/null
+++ b/include/target/target_core_plugin.h
@@ -0,0 +1,73 @@
+/*******************************************************************************
+ * Filename: target_core_plugin.h
+ *
+ * Copyright (c) 2006-2007 SBE, Inc. All Rights Reserved.
+ * Copyright (c) 2007-2009 Rising Tide Software, Inc.
+ * Copyright (c) 2008-2009 Linux-iSCSI.org
+ *
+ * Nicholas A. Bellinger <nab@kernel.org>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
+ *
+ ******************************************************************************/
+
+
+#ifndef TARGET_CORE_PLUGIN_H
+#define TARGET_CORE_PLUGIN_H
+
+#define PLUGIN_TYPE_TRANSPORT 0
+#define PLUGIN_TYPE_OBJ 1
+
+#define MAX_PLUGINS 32
+#define MAX_PLUGIN_CLASSES 16
+#define MAX_PLUGIN_CLASS_NAME 16
+#define MAX_PLUGIN_NAME 16
+
+#define PLUGIN_FREE 0
+#define PLUGIN_REGISTERED 1
+
+extern se_global_t *se_global;
+
+extern void plugin_load_all_classes(void);
+extern struct se_plugin_class_s *plugin_get_class(u32);
+extern int plugin_register_class(u32, unsigned char *, int);
+extern int plugin_deregister_class(u32);
+extern void plugin_unload_all_classes(void);
+extern void *plugin_get_obj(u32, u32, int *);
+extern struct se_plugin_s *plugin_register(void *, u32, unsigned char *, u32,
+ void (*get_plugin_info)(void *, char *, int *),
+ int (*plugin_init)(void),
+ void (*plugin_free)(void), int *);
+extern int plugin_deregister(u32, u32);
+
+typedef struct se_plugin_class_s {
+ unsigned char plugin_class_name[MAX_PLUGIN_CLASS_NAME];
+ u32 plugin_class;
+ u32 max_plugins;
+ struct se_plugin_s *plugin_array;
+ spinlock_t plugin_lock;
+} se_plugin_class_t;
+
+typedef struct se_plugin_s {
+ unsigned char plugin_name[MAX_PLUGIN_NAME];
+ int plugin_state;
+ u32 plugin_type;
+ se_plugin_class_t *plugin_class;
+ void *plugin_obj;
+ void (*get_plugin_info)(void *, char *, int *);
+ void (*plugin_free)(void);
+} se_plugin_t;
+
+#endif /* TARGET_CORE_PLUGIN_H */
^ permalink raw reply [flat|nested] 2+ messages in thread
* [RFC PATCH 8/19] Target_Core_Mod Subsystem and SE Object plugin infrastructure
@ 2009-09-12 1:56 Nicholas A. Bellinger
0 siblings, 0 replies; 2+ messages in thread
From: Nicholas A. Bellinger @ 2009-09-12 1:56 UTC (permalink / raw)
To: LKML, linux-scsi
Cc: Andrew Morton, Greg KH, Douglas Gilbert, James Bottomley,
Hannes Reinecke, FUJITA Tomonori, Mike Christie, Joel Becker,
Martin K. Petersen, Christoph Hellwig, Linus Torvalds,
Alan Stern, Boaz Harrosh, Florian Haas, Philipp Reisner
[RFC PATCH 8/19] Target_Core_Mod Subsystem and SE Object plugin infrastructure
This patch adds the simple plugin infrastructure used by subsystem and seobj plugins.
Signed-off-by: Nicholas A. Bellinger <nab@linux-iscsi.org>
diff --git a/drivers/target/target_core_plugin.c b/drivers/target/target_core_plugin.c
new file mode 100644
index 0000000..9f7ea97
--- /dev/null
+++ b/drivers/target/target_core_plugin.c
@@ -0,0 +1,326 @@
+/*******************************************************************************
+ * Filename: target_core_plugin.c
+ *
+ * Copyright (c) 2006-2007 SBE, Inc. All Rights Reserved.
+ * Copyright (c) 2007-2009 Rising Tide Software, Inc.
+ * Copyright (c) 2008-2009 Linux-iSCSI.org
+ *
+ * Nicholas A. Bellinger <nab@kernel.org>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
+ *
+ ******************************************************************************/
+
+#define TARGET_CORE_PLUGIN_C
+
+#include <linux/net.h>
+#include <linux/string.h>
+#include <linux/timer.h>
+#include <linux/slab.h>
+#include <linux/spinlock.h>
+#include <linux/smp_lock.h>
+#include <linux/in.h>
+#include <net/sock.h>
+#include <net/tcp.h>
+
+#include <target/target_core_base.h>
+#include <target/target_core_hba.h>
+#include <target/target_core_seobj.h>
+#include <target/target_core_transport.h>
+#include <target/target_core_plugin.h>
+
+#undef TARGET_CORE_PLUGIN_C
+
+void plugin_load_all_classes(void)
+{
+ /*
+ * Setup Transport Plugins
+ */
+ plugin_register_class(PLUGIN_TYPE_TRANSPORT, "TRANSPORT", MAX_PLUGINS);
+ transport_load_plugins();
+
+ /*
+ * Setup Storage Engine Object Plugins
+ */
+ plugin_register_class(PLUGIN_TYPE_OBJ, "OBJ", MAX_PLUGINS);
+ se_obj_load_plugins();
+}
+EXPORT_SYMBOL(plugin_load_all_classes);
+
+se_plugin_class_t *plugin_get_class(
+ u32 plugin_class_type)
+{
+ se_plugin_class_t *pc;
+
+ if (plugin_class_type > MAX_PLUGIN_CLASSES) {
+ printk(KERN_ERR "Passed plugin class type: %u exceeds"
+ " MAX_PLUGIN_CLASSES: %d\n", plugin_class_type,
+ MAX_PLUGIN_CLASSES);
+ return NULL;
+ }
+
+ pc = &se_global->plugin_class_list[plugin_class_type];
+ if (!pc->plugin_array)
+ return NULL;
+
+ return pc;
+}
+
+int plugin_register_class(
+ u32 plugin_class_type,
+ unsigned char *plugin_class_name,
+ int max_plugins)
+{
+ u32 i;
+ se_plugin_class_t *pc;
+ se_plugin_t *p;
+
+ if (strlen(plugin_class_name) > MAX_PLUGIN_CLASS_NAME) {
+ printk(KERN_ERR "plugin_class_name exceeds MAX_PLUGIN_CLASS"
+ "_NAME: %u\n", MAX_PLUGIN_CLASS_NAME);
+ return -1;
+ }
+ spin_lock(&se_global->plugin_class_lock);
+ if (plugin_class_type > MAX_PLUGIN_CLASSES) {
+ printk(KERN_ERR "Passed plugin class type: %u exceeds"
+ " MAX_PLUGIN_CLASSES: %d\n", plugin_class_type,
+ MAX_PLUGIN_CLASSES);
+ return -1;
+ }
+
+ pc = &se_global->plugin_class_list[plugin_class_type];
+ if (pc->plugin_array) {
+ printk(KERN_ERR "Plugin Class Type: %u already exists\n",
+ plugin_class_type);
+ return -1;
+ }
+ spin_unlock(&se_global->plugin_class_lock);
+
+ pc->plugin_array = kzalloc(sizeof(se_plugin_t) * max_plugins,
+ GFP_KERNEL);
+ if (!(pc->plugin_array)) {
+ printk(KERN_ERR "Unable to locate pc->plugin_array\n");
+ return -1;
+ }
+
+ spin_lock_init(&pc->plugin_lock);
+ pc->max_plugins = max_plugins;
+ pc->plugin_class = plugin_class_type;
+ snprintf(pc->plugin_class_name, MAX_PLUGIN_CLASS_NAME,
+ "%s", plugin_class_name);
+
+ for (i = 0; i < max_plugins; i++) {
+ p = &pc->plugin_array[i];
+ p->plugin_class = pc;
+ }
+
+ printk(KERN_INFO "SE_PC[%u] - Registered Plugin Class: %s\n",
+ pc->plugin_class, pc->plugin_class_name);
+
+ return 0;
+}
+EXPORT_SYMBOL(plugin_register_class);
+
+int plugin_deregister_class(u32 plugin_class_type)
+{
+ int i;
+ se_plugin_class_t *pc;
+ se_plugin_t *p;
+
+ pc = plugin_get_class(plugin_class_type);
+ if (!(pc))
+ return -1;
+
+ for (i = 0; i < MAX_PLUGINS; i++) {
+ p = &pc->plugin_array[i];
+
+ if (!p->plugin_obj)
+ continue;
+
+ plugin_deregister(i, plugin_class_type);
+ }
+
+ kfree(pc->plugin_array);
+ pc->plugin_array = NULL;
+
+ return 0;
+}
+EXPORT_SYMBOL(plugin_deregister_class);
+
+void plugin_unload_all_classes(void)
+{
+ u32 i;
+ se_plugin_class_t *pc;
+
+ for (i = 0; i < MAX_PLUGIN_CLASSES; i++) {
+ pc = &se_global->plugin_class_list[i];
+
+ if (!pc->plugin_array)
+ continue;
+
+ plugin_deregister_class(i);
+ }
+
+ return;
+}
+EXPORT_SYMBOL(plugin_unload_all_classes);
+
+void *plugin_get_obj(
+ u32 plugin_class,
+ u32 plugin_loc,
+ int *ret)
+{
+ se_plugin_class_t *pc;
+ se_plugin_t *p;
+
+ pc = plugin_get_class(plugin_class);
+ if (!(pc))
+ return NULL;
+
+ spin_lock(&pc->plugin_lock);
+ if (plugin_loc > pc->max_plugins) {
+ printk(KERN_ERR "Passed plugin_loc: %d exceeds"
+ " pc->max_plugins: %d\n", plugin_loc, pc->max_plugins);
+ goto out;
+ }
+
+ p = &pc->plugin_array[plugin_loc];
+ if (!p->plugin_obj) {
+ printk(KERN_ERR "Passed plugin_loc: %u does not exist!\n",
+ plugin_loc);
+ goto out;
+ }
+ spin_unlock(&pc->plugin_lock);
+
+ *ret = 0;
+ return p->plugin_obj;
+out:
+ *ret = -1;
+ spin_unlock(&pc->plugin_lock);
+ return NULL;
+}
+EXPORT_SYMBOL(plugin_get_obj);
+
+struct se_plugin_s *plugin_register(
+ void *obj,
+ u32 plugin_loc,
+ unsigned char *plugin_name,
+ u32 plugin_class,
+ void (*get_plugin_info)(void *, char *, int *),
+ int (*plugin_init)(void),
+ void (*plugin_free)(void),
+ int *ret)
+{
+ se_plugin_class_t *pc;
+ se_plugin_t *p;
+ int err;
+
+ if (!obj) {
+ printk(KERN_ERR "obj or plugin_class pointers are NULL!\n");
+ return NULL;
+ }
+
+ if (strlen(plugin_name) > MAX_PLUGIN_NAME) {
+ printk(KERN_ERR "plugin_name exceeds MAX_PLUGIN_NAME: %u\n",
+ MAX_PLUGIN_NAME);
+ return NULL;
+ }
+
+ pc = plugin_get_class(plugin_class);
+ if (!(pc))
+ return NULL;
+
+ spin_lock(&pc->plugin_lock);
+ if (plugin_loc > pc->max_plugins) {
+ printk(KERN_ERR "Passed plugin_loc: %u exceeds pc->max_plugins:"
+ " %d\n", plugin_loc, pc->max_plugins);
+ *ret = -1;
+ goto out;
+ }
+
+ p = &pc->plugin_array[plugin_loc];
+ if (p->plugin_obj) {
+ printk(KERN_ERR "Passed plugin_loc: %u already registered\n",
+ plugin_loc);
+ *ret = -1;
+ goto out;
+ }
+
+ p->plugin_obj = obj;
+ p->get_plugin_info = get_plugin_info;
+ p->plugin_free = plugin_free;
+ p->plugin_state = PLUGIN_REGISTERED;
+ p->plugin_type = plugin_loc;
+ snprintf(p->plugin_name, MAX_PLUGIN_NAME, "%s", plugin_name);
+
+ printk(KERN_INFO "PLUGIN_%s[%u] - %s registered\n",
+ pc->plugin_class_name, plugin_loc, plugin_name);
+ spin_unlock(&pc->plugin_lock);
+
+ if (*plugin_init != NULL) {
+ err = (*plugin_init)();
+ if (err) {
+ plugin_deregister(plugin_loc, plugin_class);
+ return NULL;
+ }
+ }
+
+ return p;
+
+out:
+ spin_unlock(&pc->plugin_lock);
+ return NULL;
+}
+EXPORT_SYMBOL(plugin_register);
+
+int plugin_deregister(
+ u32 plugin_loc,
+ u32 plugin_class)
+{
+ int ret = 0;
+ se_plugin_class_t *pc;
+ se_plugin_t *p;
+
+ pc = plugin_get_class(plugin_class);
+ if (!(pc))
+ return -1;
+
+ spin_lock(&pc->plugin_lock);
+ if (plugin_loc > pc->max_plugins) {
+ printk(KERN_ERR "Passed plugin_loc: %u exceeds pc->max_plugins:"
+ " %d\n", plugin_loc, pc->max_plugins);
+ ret = -1;
+ goto out;
+ }
+
+ p = &pc->plugin_array[plugin_loc];
+ if (!p->plugin_obj) {
+ printk(KERN_ERR "Passed plugin_loc: %u not active!\n",
+ plugin_loc);
+ ret = -1;
+ goto out;
+ }
+ spin_unlock(&pc->plugin_lock);
+
+ if (p->plugin_free)
+ p->plugin_free();
+
+ spin_lock(&pc->plugin_lock);
+ p->plugin_obj = NULL;
+ p->plugin_state = PLUGIN_FREE;
+out:
+ spin_unlock(&pc->plugin_lock);
+ return ret;
+}
diff --git a/include/target/target_core_plugin.h b/include/target/target_core_plugin.h
new file mode 100644
index 0000000..bc3333b
--- /dev/null
+++ b/include/target/target_core_plugin.h
@@ -0,0 +1,73 @@
+/*******************************************************************************
+ * Filename: target_core_plugin.h
+ *
+ * Copyright (c) 2006-2007 SBE, Inc. All Rights Reserved.
+ * Copyright (c) 2007-2009 Rising Tide Software, Inc.
+ * Copyright (c) 2008-2009 Linux-iSCSI.org
+ *
+ * Nicholas A. Bellinger <nab@kernel.org>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
+ *
+ ******************************************************************************/
+
+
+#ifndef TARGET_CORE_PLUGIN_H
+#define TARGET_CORE_PLUGIN_H
+
+#define PLUGIN_TYPE_TRANSPORT 0
+#define PLUGIN_TYPE_OBJ 1
+
+#define MAX_PLUGINS 32
+#define MAX_PLUGIN_CLASSES 16
+#define MAX_PLUGIN_CLASS_NAME 16
+#define MAX_PLUGIN_NAME 16
+
+#define PLUGIN_FREE 0
+#define PLUGIN_REGISTERED 1
+
+extern se_global_t *se_global;
+
+extern void plugin_load_all_classes(void);
+extern struct se_plugin_class_s *plugin_get_class(u32);
+extern int plugin_register_class(u32, unsigned char *, int);
+extern int plugin_deregister_class(u32);
+extern void plugin_unload_all_classes(void);
+extern void *plugin_get_obj(u32, u32, int *);
+extern struct se_plugin_s *plugin_register(void *, u32, unsigned char *, u32,
+ void (*get_plugin_info)(void *, char *, int *),
+ int (*plugin_init)(void),
+ void (*plugin_free)(void), int *);
+extern int plugin_deregister(u32, u32);
+
+typedef struct se_plugin_class_s {
+ unsigned char plugin_class_name[MAX_PLUGIN_CLASS_NAME];
+ u32 plugin_class;
+ u32 max_plugins;
+ struct se_plugin_s *plugin_array;
+ spinlock_t plugin_lock;
+} se_plugin_class_t;
+
+typedef struct se_plugin_s {
+ unsigned char plugin_name[MAX_PLUGIN_NAME];
+ int plugin_state;
+ u32 plugin_type;
+ se_plugin_class_t *plugin_class;
+ void *plugin_obj;
+ void (*get_plugin_info)(void *, char *, int *);
+ void (*plugin_free)(void);
+} se_plugin_t;
+
+#endif /* TARGET_CORE_PLUGIN_H */
^ permalink raw reply [flat|nested] 2+ messages in thread
end of thread, other threads:[~2009-09-18 22:12 UTC | newest]
Thread overview: 2+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2009-09-18 22:08 [RFC PATCH 8/19] Target_Core_Mod Subsystem and SE Object plugin infrastructure Nicholas A. Bellinger
-- strict thread matches above, loose matches on Subject: below --
2009-09-12 1:56 Nicholas A. Bellinger
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox
all inboxes | Powered by JetHome®