Whamcloud - gitweb
b=19706 porting patch for master.
[fs/lustre-release.git] / libcfs / include / libcfs / params_tree.h
index d6bf464..635d6bc 100644 (file)
@@ -81,16 +81,38 @@ typedef struct poll_table_struct                cfs_poll_table_t;
 
 /* in lprocfs_stat.c, to protect the private data for proc entries */
 extern cfs_rw_semaphore_t       _lprocfs_lock;
+
+/* to begin from 2.6.23, Linux defines self file_operations (proc_reg_file_ops)
+ * in procfs, the proc file_operation defined by Lustre (lprocfs_generic_fops)
+ * will be wrapped into the new defined proc_reg_file_ops, which instroduces
+ * user count in proc_dir_entrey(pde_users) to protect the proc entry from
+ * being deleted. then the protection lock (_lprocfs_lock) defined by Lustre
+ * isn't necessary anymore for lprocfs_generic_fops(e.g. lprocfs_fops_read).
+ * see bug19706 for detailed information.
+ */
+#ifndef HAVE_PROCFS_USERS
+
 #define LPROCFS_ENTRY()                 \
 do {                                    \
         cfs_down_read(&_lprocfs_lock);  \
 } while(0)
+
 #define LPROCFS_EXIT()                  \
 do {                                    \
         cfs_up_read(&_lprocfs_lock);    \
 } while(0)
 
+#else
+#define LPROCFS_ENTRY() do{ }while(0)
+#define LPROCFS_EXIT()  do{ }while(0)
+#endif
+
 #ifdef HAVE_PROCFS_DELETED
+
+#ifdef HAVE_PROCFS_USERS
+#error proc_dir_entry->deleted is conflicted with proc_dir_entry->pde_users
+#endif
+
 static inline
 int LPROCFS_ENTRY_AND_CHECK(struct proc_dir_entry *dp)
 {
@@ -101,6 +123,19 @@ int LPROCFS_ENTRY_AND_CHECK(struct proc_dir_entry *dp)
         }
         return 0;
 }
+#elif defined(HAVE_PROCFS_USERS) /* !HAVE_PROCFS_DELETED*/
+static inline
+int LPROCFS_ENTRY_AND_CHECK(struct proc_dir_entry *dp)
+{
+        int deleted = 0;
+        spin_lock(&(dp)->pde_unload_lock);
+        if (dp->proc_fops == NULL)
+                deleted = 1;
+        spin_unlock(&(dp)->pde_unload_lock);
+        if (deleted)
+                return -ENODEV;
+        return 0;
+}
 #else /* !HAVE_PROCFS_DELETED*/
 static inline
 int LPROCFS_ENTRY_AND_CHECK(struct proc_dir_entry *dp)
@@ -109,16 +144,25 @@ int LPROCFS_ENTRY_AND_CHECK(struct proc_dir_entry *dp)
         return 0;
 }
 #endif /* HAVE_PROCFS_DELETED */
+#define LPROCFS_SRCH_ENTRY()            \
+do {                                    \
+        down_read(&_lprocfs_lock);      \
+} while(0)
+
+#define LPROCFS_SRCH_EXIT()             \
+do {                                    \
+        up_read(&_lprocfs_lock);        \
+} while(0)
 
 #define LPROCFS_WRITE_ENTRY()           \
 do {                                    \
         cfs_down_write(&_lprocfs_lock); \
 } while(0)
+
 #define LPROCFS_WRITE_EXIT()            \
 do {                                    \
         cfs_up_write(&_lprocfs_lock);   \
 } while(0)
-
 #else /* !LPROCFS */
 
 typedef struct cfs_params_file {