summaryrefslogtreecommitdiffstats
path: root/src/usr
diff options
context:
space:
mode:
authorDoug Gilbert <dgilbert@us.ibm.com>2012-01-13 09:40:41 -0600
committerDouglas R. Gilbert <dgilbert@us.ibm.com>2012-01-19 14:47:50 -0600
commit11a2e07a97bb44005dfd8fe8bac690014b3e2a81 (patch)
tree3a8492a5476e540ced0cbb7cb21c8d16b0936f9f /src/usr
parent67ab5c65b2caabff6147143a90ab5584573e24ae (diff)
downloadblackbird-hostboot-11a2e07a97bb44005dfd8fe8bac690014b3e2a81.tar.gz
blackbird-hostboot-11a2e07a97bb44005dfd8fe8bac690014b3e2a81.zip
VFS add functions to find module by address and query if module is loaded
Change-Id: I471a2a773d42f11ab973f42ca701c8be5191d776 Reviewed-on: http://gfw160.austin.ibm.com:8080/gerrit/611 Tested-by: Jenkins Server Reviewed-by: Daniel M. Crowell <dcrowell@us.ibm.com> Reviewed-by: Douglas R. Gilbert <dgilbert@us.ibm.com>
Diffstat (limited to 'src/usr')
-rw-r--r--src/usr/vfs/test/vfstest.H32
-rw-r--r--src/usr/vfs/vfsrp.C113
-rw-r--r--src/usr/vfs/vfsrp.H26
3 files changed, 156 insertions, 15 deletions
diff --git a/src/usr/vfs/test/vfstest.H b/src/usr/vfs/test/vfstest.H
index 5e33a0b33..3f9644f27 100644
--- a/src/usr/vfs/test/vfstest.H
+++ b/src/usr/vfs/test/vfstest.H
@@ -71,6 +71,38 @@ class VfsTest: public CxxTest::TestSuite
TS_FAIL("module_unload failed");
}
}
+
+ void test_findModule(void)
+ {
+ size_t size = 0;
+ const char * addr = NULL;
+ const char * name = "testdata";
+
+ errlHndl_t err = VFS::module_address(name , addr, size);
+ if (err)
+ {
+ TS_FAIL("module_address failed");
+ ERRORLOG::errlCommit(err,VFS_COMP_ID);
+ }
+
+ name = VFS::module_find_name(addr);
+ TS_TRACE("VFS module @ %p is %s",addr,name);
+
+ if(strcmp(name,"testdata") != 0)
+ {
+ TS_FAIL("VFS find module by address failed!");
+ }
+
+ if(VFS::module_is_loaded(name))
+ {
+ TS_TRACE("VFS module %s is loaded",name);
+ TS_FAIL("VFS module should NOT be loaded");
+ }
+ else
+ {
+ TS_TRACE("VFS module %s is not loaded",name);
+ }
+ }
};
diff --git a/src/usr/vfs/vfsrp.C b/src/usr/vfs/vfsrp.C
index e060c7b80..be9364965 100644
--- a/src/usr/vfs/vfsrp.C
+++ b/src/usr/vfs/vfsrp.C
@@ -263,33 +263,56 @@ void VfsRp::_load_unload(msg_t * i_msg)
{
int rc = 0;
+ // don't want the possibility of a function called in this module
+ // until it's completely loaded and inited, so hold
+ // off any query or other operation.
+ mutex_lock(&iv_mutex);
+
+ ModuleList_t::iterator mod_itr =
+ std::find(iv_loaded.begin(),iv_loaded.end(),module);
+
if(i_msg->type == VFS_MSG_LOAD)
{
- rc = vfs_module_perms(module);
-
- if(!rc)
+ if(mod_itr == iv_loaded.end()) // make sure it's not already loaded
{
- if(module->init)
+ // Set mem access parms
+ rc = vfs_module_perms(module);
+ if(!rc)
{
- (module->init)(NULL);
+ iv_loaded.push_back(module);
+
+ if(module->init)
+ {
+ (module->init)(NULL);
+ }
+
}
}
}
else // unload
{
- if(module->fini)
+ if(mod_itr != iv_loaded.end()) // Loaded
{
- (module->fini)(NULL);
- }
+ iv_loaded.erase(mod_itr);
- rc = mm_set_permission(module->text,
- ALIGN_PAGE(module->byte_count),
- NO_ACCESS);
+ if(module->fini)
+ {
+ (module->fini)(NULL);
+ }
+
+ rc = mm_set_permission(module->text,
+ ALIGN_PAGE(module->byte_count),
+ NO_ACCESS);
- rc = mm_remove_pages(RELEASE,
- module->text,
- ALIGN_PAGE(module->byte_count));
+ rc = mm_remove_pages(RELEASE,
+ module->text,
+ ALIGN_PAGE(module->byte_count));
+ }
+ // else module was not loaded
}
+
+ mutex_unlock(&iv_mutex);
+
if(rc)
{
/*@ errorlog tag
@@ -399,6 +422,57 @@ const VfsSystemModule * VfsRp::get_vfs_info(const char * i_name) const
// ----------------------------------------------------------------------------
+const char * VfsRp::get_name_from_address(const void * i_vaddr) const
+{
+ const char * result = NULL;
+
+ VfsSystemModule * module = vfs_find_address
+ ((VfsSystemModule *)(iv_pnor_vaddr + VFS_EXTENDED_MODULE_TABLE_OFFSET),
+ i_vaddr);
+
+ if(!module) // look in the base modules
+ {
+ module = vfs_find_address(VFS_MODULES,i_vaddr);
+ }
+ if(module)
+ {
+ result = module->module;
+ }
+ return result;
+}
+
+// ----------------------------------------------------------------------------
+
+bool VfsRp::is_module_loaded(const char * i_name)
+{
+ bool result = false;
+ const VfsSystemModule * module = get_vfs_info(i_name);
+ if(module)
+ {
+ mutex_lock(&iv_mutex);
+ ModuleList_t::const_iterator i =
+ std::find(iv_loaded.begin(),iv_loaded.end(),module);
+ if(i != iv_loaded.end())
+ {
+ result = true;
+ }
+ mutex_unlock(&iv_mutex);
+ }
+ if(!result) // look in the base
+ {
+ module = vfs_find_module(VFS_MODULES,i_name);
+ if(module)
+ {
+ // all base modules are always loaded
+ result = true;
+ }
+ }
+
+ return result;
+}
+
+// ----------------------------------------------------------------------------
+
void VfsRp::get_test_modules(std::vector<const char *> & o_list) const
{
o_list.clear();
@@ -518,3 +592,14 @@ errlHndl_t VFS::module_address(const char * i_name, const char *& o_address, siz
return err;
}
+const char * VFS::module_find_name(const void * i_vaddr)
+{
+ return Singleton<VfsRp>::instance().get_name_from_address(i_vaddr);
+}
+
+bool VFS::module_is_loaded(const char * i_name)
+{
+ return Singleton<VfsRp>::instance().is_module_loaded(i_name);
+}
+
+
diff --git a/src/usr/vfs/vfsrp.H b/src/usr/vfs/vfsrp.H
index c5a74c91f..8492f559d 100644
--- a/src/usr/vfs/vfsrp.H
+++ b/src/usr/vfs/vfsrp.H
@@ -27,6 +27,8 @@
#include <builtins.h>
#include <errl/errltypes.H>
#include <sys/msg.h>
+#include <vector>
+#include <sys/sync.h>
struct msg_t;
@@ -68,11 +70,28 @@ namespace VFS
*/
const VfsSystemModule * get_vfs_info(const char * i_name) const;
+ /**
+ * Get the module name that contains the given address
+ * @param[in] i_vaddr The virtual address
+ * @return ptr to the module name or NULL if it's not found
+ */
+ const char * get_name_from_address(const void * i_vaddr) const;
+
+ /**
+ * Query if a module is loaded
+ * @param[in] i_name The module name
+ * @return [true|false]
+ */
+ bool is_module_loaded(const char * i_name);
+
protected:
/**
* Ctor
*/
- VfsRp() : iv_msgQ(NULL), iv_pnor_vaddr(0) {}
+ VfsRp() : iv_msgQ(NULL), iv_pnor_vaddr(0)
+ {
+ mutex_init(&iv_mutex);
+ }
/**
* Dtor
@@ -127,6 +146,11 @@ namespace VFS
msg_q_t iv_msgQ; //!< message queue
uint64_t iv_pnor_vaddr; //!< virtual address of ext image in PFNOR
+
+ typedef std::vector<VfsSystemModule *> ModuleList_t;
+
+ mutex_t iv_mutex; //!< lock for iv_loaded
+ ModuleList_t iv_loaded; //!< Loaded modules
};
}; // VFS namepsace
OpenPOWER on IntegriCloud