Skip to content

Instantly share code, notes, and snippets.

@Varriount
Created May 1, 2014 20:12
Show Gist options
  • Save Varriount/941fcda927679af9ae89 to your computer and use it in GitHub Desktop.
Save Varriount/941fcda927679af9ae89 to your computer and use it in GitHub Desktop.
filemon.nim
import winlean, os, asyncdispatch
# Associate a directory handle with an IO completion port
# Create a buffer to store file changes
# Call the ReadDirectoryChanges
proc openAsyncHandle(path: string, followSymlink=true): TAsyncFD =
var flags = (FILE_FLAG_BACKUP_SEMANTICS or
FILE_FLAG_OVERLAPPED)
if not followSymlink:
flags = flags or FILE_FLAG_OPEN_REPARSE_POINT
when useWinUnicode:
result = createFileW(
newWideCString(path), 0'i32,
FILE_SHARE_DELETE or FILE_SHARE_READ or FILE_SHARE_WRITE,
nil, OPEN_EXISTING, flags, 0
).TAsyncFD
else:
result = createFileA(
path, 0'i32,
FILE_SHARE_DELETE or FILE_SHARE_READ or FILE_SHARE_WRITE,
nil, OPEN_EXISTING, flags, 0
).TAsyncFD
if result == INVALID_HANDLE_VALUE.TAsyncFD:
osError(osLastError())
proc main =
var
dirName = r".\"
dirHandle = openAsyncHandle(dirName)
aligned: tuple [alignIt: int32, buffer: array [2000, byte]]
bufferLen: int32 = aligned.buffer.len().int32
filterFlags = (FILE_NOTIFY_CHANGE_FILE_NAME or
FILE_NOTIFY_CHANGE_DIR_NAME or
FILE_NOTIFY_CHANGE_ATTRIBUTES or
FILE_NOTIFY_CHANGE_SIZE
)
ol = cast[PCustomOverlapped](alloc0(sizeof(TCustomOverlapped)))
ol.data = TCompletionData(sock: dirHandle, cb:
proc (sock: TAsyncFD, bytesCount: DWord, errcode: TOSErrorCode) =
sock.repr.echo
bytesCount.echo
errcode.echo
)
dirHandle.register()
osLastError().echo
let r = ReadDirectoryChangesW(dirHandle.THandle,
addr aligned.buffer[0],
bufferLen,
false.winbool,
filterFlags,
cast[ptr dword](nil),
cast[POverlapped](ol),
cast[LPOVERLAPPED_COMPLETION_ROUTINE](nil)
)
osLastError().echo()
if r == 0:
osError(osLastError())
while true:
poll()
when isMainModule:
main()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment