prevent CNAME/PTR parsing from reading data past the response end
[musl] / src / stdio / __lockfile.c
index 4e0239e..0f60a14 100644 (file)
@@ -1,20 +1,23 @@
 #include "stdio_impl.h"
 #include "pthread_impl.h"
 
-void __lockfile(FILE *f)
+int __lockfile(FILE *f)
 {
-       int spins=100000;
-       int tid;
-
-       if (f->lock < 0) return;
-       tid = __pthread_self()->tid;
-       if (f->lock == tid) {
-               while (f->lockcount == INT_MAX);
-               f->lockcount++;
-               return;
+       int owner = f->lock, tid = __pthread_self()->tid;
+       if ((owner & ~MAYBE_WAITERS) == tid)
+               return 0;
+       owner = a_cas(&f->lock, 0, tid);
+       if (!owner) return 1;
+       while ((owner = a_cas(&f->lock, 0, tid|MAYBE_WAITERS))) {
+               if ((owner & MAYBE_WAITERS) ||
+                   a_cas(&f->lock, owner, owner|MAYBE_WAITERS)==owner)
+                       __futexwait(&f->lock, owner|MAYBE_WAITERS, 1);
        }
-       while (a_cas(&f->lock, 0, tid))
-               if (spins) spins--, a_spin();
-               else __syscall(SYS_sched_yield);
-       f->lockcount = 1;
+       return 1;
+}
+
+void __unlockfile(FILE *f)
+{
+       if (a_swap(&f->lock, 0) & MAYBE_WAITERS)
+               __wake(&f->lock, 1, 1);
 }