|
| 1 | +import asyncio |
1 | 2 | import atomics |
2 | 3 | from multiprocessing import shared_memory |
3 | 4 | from lightllm.utils.log_utils import init_logger |
@@ -41,18 +42,40 @@ class AtomicLockItem: |
41 | 42 | def __init__(self, context: AtomicShmArrayLock, index: int): |
42 | 43 | self.context = context |
43 | 44 | self.index = index |
| 45 | + self._buf = context.shm.buf[index * 4 : (index + 1) * 4] |
| 46 | + |
| 47 | + def try_acquire(self) -> bool: |
| 48 | + with atomics.atomicview(self._buf, atype=atomics.INT) as a: |
| 49 | + return a.cmpxchg_weak(0, 1) |
| 50 | + |
| 51 | + def release(self): |
| 52 | + with atomics.atomicview(self._buf, atype=atomics.INT) as a: |
| 53 | + a.store(0) |
44 | 54 |
|
45 | 55 | def __enter__(self): |
46 | | - with atomics.atomicview( |
47 | | - buffer=self.context.shm.buf[self.index * 4 : (self.index + 1) * 4], atype=atomics.INT |
48 | | - ) as a: |
| 56 | + with atomics.atomicview(buffer=self._buf, atype=atomics.INT) as a: |
49 | 57 | while not a.cmpxchg_weak(0, 1): |
50 | 58 | pass |
51 | 59 |
|
52 | 60 | def __exit__(self, exc_type, exc_val, exc_tb): |
53 | | - with atomics.atomicview( |
54 | | - buffer=self.context.shm.buf[self.index * 4 : (self.index + 1) * 4], atype=atomics.INT |
55 | | - ) as a: |
| 61 | + with atomics.atomicview(buffer=self._buf, atype=atomics.INT) as a: |
56 | 62 | while not a.cmpxchg_weak(1, 0): |
57 | 63 | pass |
58 | 64 | return False |
| 65 | + |
| 66 | + |
| 67 | +class AsyncLock: |
| 68 | + def __init__(self, lock_item, base_delay=0.01): |
| 69 | + self._item = lock_item |
| 70 | + self._base = base_delay |
| 71 | + |
| 72 | + async def __aenter__(self): |
| 73 | + delay = self._base |
| 74 | + while True: |
| 75 | + if self._item.try_acquire(): # 尝试拿锁;成功立即返回 |
| 76 | + return |
| 77 | + await asyncio.sleep(delay) |
| 78 | + |
| 79 | + async def __aexit__(self, exc_t, exc, tb): |
| 80 | + self._item.release() |
| 81 | + return False |
0 commit comments