Search code examples
multithreadinglispcclreadwritelock

How to grab read-write-lock without releasing it in Lisp?


I'm using Clozure CL to write an app. In the app, I need to write several files, so I made a read-write-lock for each file.

Now I'm trying to write a quit function. It checks whether all the file writings are complete and then quit. Basically it works like below:

  1. Grab all the files read-write-locks
  2. Quit CCL

I read the Clozure CL document, but can't find any function like grab-write-lock. I can only find "grab-lock", "with-read-lock" and "with-write-lock". 'grab-lock' won't work on read-write-lock, the other two will release the lock automatically. So how can I grab all the file read-write-locks (not release them) and quit the app?


Solution

  • I'm not all that familiar with Clozure CL's locking mechanisms, but I think that some macroexpansion can illustrate at least one way to do this:

    CL-USER> (pprint (macroexpand-1 '(with-write-lock (my-lock)
                                      do-something)))
    
    (CCL::WITH-LOCK-CONTEXT
      (LET* ((#:G350 (MAKE-LOCK-ACQUISITION))
             (#:G351 MY-LOCK))
        (DECLARE (DYNAMIC-EXTENT #:G350))
        (UNWIND-PROTECT
            (PROGN
              (CCL::WRITE-LOCK-RWLOCK #:G351 #:G350)
              DO-SOMETHING)
          (WHEN (CCL::LOCK-ACQUISITION.STATUS #:G350)
            (CCL::UNLOCK-RWLOCK #:G351)))))
    

    I can't say whether this (using ccl::with-lock-context/ccl::write-lock-rwlock) is a good way to do this in your own code or not, but it's certainly a way to do it.