Re: [patch] down_norecurse(), down_interruptible_norecurse(), up_norecurse()

Andrea Arcangeli (andrea@e-mind.com)
Sat, 30 Jan 1999 19:34:33 +0100 (CET)


On Sat, 30 Jan 1999, Andrea Arcangeli wrote:

> BTW, MUTEX_LOCKED used with recursive semaphores (2.2.1) is not likely to
> make a lot of sense (to me at least) and the code that is using it should
> be probably reviewed (e.g. ide_do_drive_cmd(), ide_end_drive_cmd()). Code
> that is using MUTEX_LOCKED is likely to want to be converted to
> norecursive semaphores. Personally I would remove MUTEX_LOCKED and I would
> left only MUTEX, MUTEX_NORECURSE and MUTEX_LOCKED_NORECURSE... I'll do
> that here soon but I am not going to post my future changes on the list
> even if I am worried by such _potential_ bogus semaphores usages.

For help myeslf in the move from recursive to norecursive semaphores of
some code I added a struct semaphore_norecurse, that it's the same but it
will cause the compiler to avoid me to make mistakes.

This is the _shorter_ diff I can produce to put back norecursive
semaphores in the kernel (this time without riking to do mistakes between
norecursive and recursive functions):

Index: include/asm/semaphore.h
===================================================================
RCS file: /var/cvs/linux/include/asm-i386/semaphore.h,v
retrieving revision 1.1.2.4
diff -u -r1.1.2.4 semaphore.h
--- semaphore.h 1999/01/25 20:40:02 1.1.2.4
+++ semaphore.h 1999/01/30 18:24:59
@@ -47,11 +47,17 @@
* Other (saner) architectures would use "wmb()" and "rmb()" to
* do this in a more obvious manner.
*/
-struct semaphore {
- atomic_t count;
- unsigned long owner, owner_depth;
- int waking;
+#define STRUCT_SEMAPHORE \
+ atomic_t count; \
+ unsigned long owner, owner_depth; \
+ int waking; \
struct wait_queue * wait;
+
+struct semaphore {
+ STRUCT_SEMAPHORE
+};
+struct semaphore_norecurse {
+ STRUCT_SEMAPHORE
};

/*
@@ -66,6 +72,8 @@

#define MUTEX ((struct semaphore) { ATOMIC_INIT(1), 0, 0, 0, NULL })
#define MUTEX_LOCKED ((struct semaphore) { ATOMIC_INIT(0), 0, 1, 0, NULL })
+#define MUTEX_NORECURSE ((struct semaphore_norecurse) { ATOMIC_INIT(1), 0, 0, 0, NULL })
+#define MUTEX_LOCKED_NORECURSE ((struct semaphore_norecurse) { ATOMIC_INIT(0), 0, 0, 0, NULL })

asmlinkage void __down_failed(void /* special register calling convention */);
asmlinkage int __down_failed_interruptible(void /* params in registers */);
@@ -209,6 +217,69 @@
__asm__ __volatile__(
"# atomic up operation\n\t"
"decl 8(%0)\n\t"
+#ifdef __SMP__
+ "lock ; "
+#endif
+ "incl 0(%0)\n\t"
+ "jle 2f\n"
+ "1:\n"
+ ".section .text.lock,\"ax\"\n"
+ "2:\tpushl $1b\n\t"
+ "jmp __up_wakeup\n"
+ ".previous"
+ :/* no outputs */
+ :"c" (sem)
+ :"memory");
+}
+
+extern inline void down_norecurse(struct semaphore_norecurse * sem)
+{
+ __asm__ __volatile__(
+ "# atomic down operation\n\t"
+#ifdef __SMP__
+ "lock ; "
+#endif
+ "decl 0(%0)\n\t"
+ "js 2f\n\t"
+ "1:\n"
+ ".section .text.lock,\"ax\"\n"
+ "2:\tpushl $1b\n\t"
+ "jmp __down_failed\n"
+ ".previous"
+ :/* no outputs */
+ :"c" (sem)
+ :"memory");
+}
+
+extern inline int down_interruptible_norecurse(struct semaphore_norecurse * sem)
+{
+ int result;
+
+ __asm__ __volatile__(
+ "# atomic interruptible down operation\n\t"
+#ifdef __SMP__
+ "lock ; "
+#endif
+ "decl 0(%1)\n\t"
+ "js 2f\n\t"
+ "xorl %0,%0\n"
+ "1:\n"
+ ".section .text.lock,\"ax\"\n"
+ "2:\tpushl $1b\n\t"
+ "jmp __down_failed_interruptible\n"
+ ".previous"
+ :"=a" (result)
+ :"c" (sem)
+ :"memory");
+ return result;
+}
+
+extern inline void up_norecurse(struct semaphore_norecurse * sem)
+{
+ __asm__ __volatile__(
+ "movl $0,4(%0)\n\t"
+ "movl $-1,8(%0)\n\t"
+ "# atomic up operation\n\t"
#ifdef __SMP__
"lock ; "
#endif

Does somebody think as me (and Tim) that it worth to have usable
norecursive semaphores in the kernel? Am I wrong thinking that code that
start with a sem = MUTEX_LOCKED is likely to not want recursive
semaphores beahvior?

Andrea Arcangeli

-
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@vger.rutgers.edu
Please read the FAQ at http://www.tux.org/lkml/