Hi All,
I would like to understand the behavior of CcCoherencyFlushAndPurgeCache in
the following scenario:
- I have a memory-mapped file with caching/buffering enabled.
- I have not executed CcInitializeCacheMap on the file.
- After doing some X read/write operations, I perform
CcCoherencyFlushAndPurgeCache on the file with a valid FileOffsert and
Length.
- The call completes successfully when the passed VArange is resident i.e.
(PDEs/PTEs are valid.). But, it fails for the VArange which has some small
regions with invalid PDEs/PTEs and I get STATUS_CACHE_PAGE_LOCKED return
code.
- Note, the regions are invalid because the system memory is
oversubscribed. OS might have paged out these regions already.
*** I see above failure only when system memory is oversubscribed.
Otherwise, everything works fine.
Is this the expected behavior of CcCoherencyFlushAndPurgeCache?
According to MSDN, CcInitializeCacheMap should be called before calling any
other CcXXXX routines. But, I am waiting for OS to do file caching. Can
this be the cause of failure?
MSDN says that, CcCoherencyFlushAndPurgeCache can fail while invalidating
the pages. But, what if the already invalidated pages (paged out/ un-mapped
pages) are passed to the call? Should it work?
I have made sure that the exclusive locking logic before the call is
correct.
Thanks.
~PM
How can you take the locks on an object you don’t own? Furthermore, why are you calling any CcXXX functions on objects you don’t own? Unless you are acting as an FSD, which you didn’t indicate in your post, I don’t think you should be doing any of these things.
Thanks for the reply, Paul. I am acting as an FSD.
Paul, I am acting as a filter driver (FD). Sorry for the confusion.
I don’t understand why can’t a filter driver do CcCoherencyFlushAndPurgeCache.
If you want to control the cache of a file object, you’ll need to create an isolation filter (also known as shadow file objects). There are plenty of posts regarding this type of filter on this list.
As for the reasons why, others have answered this better than me so here on some links.
http://www.osronline.com/showthread.cfm?link=251088
Main point from Tony: “Bottom line: if *you* don’t own the cache for a given FileObject, you should not call Cc* functions against that file object. It might work. It might not work. But in either case it violates the ownership rights of the file system that controls that file object and when it breaks you will be at fault.”
http://www.osronline.com/article.cfm?article=560
http://www.osronline.com/article.cfm?article=571
Hi Philly,
I have question here , your comment can help a lot. it is not documented
that detailed on msdn
its about how to synchronize with CcCoherencyFlushAndPurgeCache since it
is said blocking call
so what resources from AdvanceFCBheader to be acquired ?
PagingIOResource or Resource or both ( shared / exclusive )?
I tried some combination but always concerned about the Hangs …
On Sun, Jan 18, 2015 at 12:09 PM, wrote:
> I got it. Thanks.
>
> —
> NTFSD is sponsored by OSR
>
> OSR is hiring!! Info at http://www.osr.com/careers
>
> For our schedule of debugging and file system seminars visit:
> http://www.osr.com/seminars
>
> To unsubscribe, visit the List Server section of OSR Online at
> http://www.osronline.com/page.cfm?name=ListServer
>
–
मनीष आनंद सामरिया
Maneesh Anand.Samria
I am too struggling with the same. How to synchronize FSD - CcCoherencyFlushAndPurgeCache with VMM’s modified page writer and modified mapped writer?
Is this a busy hang or a resource hang? The latter shouldn’t be hard to
diagnose.
Absent any sensible documentation or example I have (for now) had to give up
calling this API and have reverted to the old & suboptimal solution. As I
recall in my case somewhere inside CcCoherencyFlushAndPurgeCache there is a
looping call to CcPurge which just goes around and around because the
CcPurge fails. I intend to try to bottom this out at plugfest with someone
who has source code access and symbols.
Also note that the documentation infers that this is a synchronous operation
when in fact it is only the IOs which are synchronous. The tear down of the
Cc structures is still posted to the lazy writer which can be unfortunate if
you are an isolating filter.
Currently, I am having hard time synchronizing this FSD-CcCoherencyFlushAndPurgeCache when VMM’s mapped page writer is invoked under memory pressure. I have forced MPW to get exclusive lock on the FCB->main Resource using flags. I acquire the same lock exclusively before calling CcCoherencyFlushAndPurgeCache. But, still the call fails with STATUS_CACHE_PAGE_LOCKED.
Note, the operation is on memory mapped file. Hence, I haven’t done ccInitializeCacheMap and cc callback implementation.
Thanks,
Prasad
I can’t help much with CcCoherencyFlushAndPurgeCache as I’ve never had to use it before. I based my isolation filter on FastFat which does not call CcCoherencyFlushAndPurgeCache.
When you examine FastFat, you can see that you need to acquire the FCB exclusively for CcPurge and the PagingIoResource exclusively when doing a CcFlush. So I’d assume you need to grab both when calling CcCoherencyFlushAndPurgeCache but again, if you don’t own the file object you shouldn’t be calling any CcXXX functions anyway.
Thanks for reply Paul. I figured the locking part. But, I still see the same issue mentioned in Message#10. I cant use ccPurge because it does not work with memory mapped files. Thanks for your help Paul.
Here is my locking model for FSD: (Note lazy writer is disabled.)
//locking over cc flush
acquireMainEx()
acquirePagingIoEx()
releasePagingIo()
ccCoherencyflushandPurge()
ReleaseMain()
//Mod Page Writer callback
acquirePagingIoShared()
releasePagingIo()
Consider a scenario:
FSD is “flushing and purging” the cache. At the same time, due to memory pressure MPW gets invoked by OS. In this case both the threads (FSD and MPW) start at the same time. This causes ccCoherencyflushandPurge() to fail as MPW might have locked pages.
In short, flush operation of MPW collides with purge of FSD. FASTFAT does the pick/drop of paging I/O to avoid such failures. But, somehow its not working in the above scenario.
If I call acquireMainEx() in the MPW callback, deadlock happens. Because, ccCoherencyFlushandPurge (which is holding acquireMainEx()) invokes MPW to write back dirty pages. I don’t understand: If lazy writer is disabled, why ccCoherencyFlushAndPurge is invoking MPW for write back and getting deadlocked?