| 
									
										
										
										
											2008-12-15 02:32:21 -05:00
										 |  |  | ! Copyright (C) 2008 Doug Coleman. | 
					
						
							|  |  |  | ! See http://factorcode.org/license.txt for BSD license. | 
					
						
							| 
									
										
										
										
											2010-12-26 03:08:57 -05:00
										 |  |  | USING: accessors alien alien.c-types alien.data alien.strings | 
					
						
							|  |  |  | alien.syntax arrays assocs classes.struct combinators | 
					
						
							|  |  |  | combinators.short-circuit continuations destructors environment | 
					
						
							|  |  |  | io io.backend io.binary io.buffers io.encodings.utf16n io.files | 
					
						
							|  |  |  | io.files.private io.files.types io.pathnames io.ports | 
					
						
							|  |  |  | io.streams.c io.streams.null io.timeouts kernel libc literals | 
					
						
							|  |  |  | locals make math math.bitwise namespaces sequences | 
					
						
							|  |  |  | specialized-arrays system threads tr windows windows.errors | 
					
						
							|  |  |  | windows.handles windows.kernel32 windows.shell32 windows.time | 
					
						
							| 
									
										
										
										
											2011-10-19 04:16:53 -04:00
										 |  |  | windows.types fry ;
 | 
					
						
							| 
									
										
										
										
											2010-09-19 15:02:32 -04:00
										 |  |  | SPECIALIZED-ARRAY: ushort | 
					
						
							| 
									
										
										
										
											2008-12-15 02:32:21 -05:00
										 |  |  | IN: io.files.windows | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2010-09-19 15:02:32 -04:00
										 |  |  | HOOK: CreateFile-flags io-backend ( DWORD -- DWORD )
 | 
					
						
							|  |  |  | HOOK: FileArgs-overlapped io-backend ( port -- overlapped/f )
 | 
					
						
							|  |  |  | HOOK: add-completion io-backend ( port -- port )
 | 
					
						
							|  |  |  | HOOK: open-append os ( path -- win32-file )
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | TUPLE: win32-file < win32-handle ptr ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | : <win32-file> ( handle -- win32-file )
 | 
					
						
							|  |  |  |     win32-file new-win32-handle ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | M: win32-file dispose | 
					
						
							|  |  |  |     [ cancel-operation ] [ call-next-method ] bi ;
 | 
					
						
							|  |  |  |      | 
					
						
							|  |  |  | : opened-file ( handle -- win32-file )
 | 
					
						
							|  |  |  |     check-invalid-handle <win32-file> |dispose add-completion ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | CONSTANT: share-mode | 
					
						
							|  |  |  |     flags{ | 
					
						
							|  |  |  |         FILE_SHARE_READ | 
					
						
							|  |  |  |         FILE_SHARE_WRITE | 
					
						
							|  |  |  |         FILE_SHARE_DELETE | 
					
						
							|  |  |  |     } | 
					
						
							|  |  |  |      | 
					
						
							|  |  |  | : default-security-attributes ( -- obj )
 | 
					
						
							|  |  |  |     SECURITY_ATTRIBUTES <struct> | 
					
						
							|  |  |  |     SECURITY_ATTRIBUTES heap-size >>nLength ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | TUPLE: FileArgs | 
					
						
							|  |  |  |     hFile lpBuffer nNumberOfBytesToRead | 
					
						
							|  |  |  |     lpNumberOfBytesRet lpOverlapped ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | C: <FileArgs> FileArgs | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | : make-FileArgs ( port -- <FileArgs> )
 | 
					
						
							|  |  |  |     { | 
					
						
							|  |  |  |         [ handle>> check-disposed ] | 
					
						
							|  |  |  |         [ handle>> handle>> ] | 
					
						
							|  |  |  |         [ buffer>> ] | 
					
						
							|  |  |  |         [ buffer>> buffer-length ] | 
					
						
							| 
									
										
										
										
											2010-12-25 19:54:45 -05:00
										 |  |  |         [ drop 0 DWORD <ref> ] | 
					
						
							| 
									
										
										
										
											2010-09-19 15:02:32 -04:00
										 |  |  |         [ FileArgs-overlapped ] | 
					
						
							|  |  |  |     } cleave <FileArgs> ;
 | 
					
						
							|  |  |  |      | 
					
						
							|  |  |  | ! Global variable with assoc mapping overlapped to threads | 
					
						
							|  |  |  | SYMBOL: pending-overlapped | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | TUPLE: io-callback port thread ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | C: <io-callback> io-callback | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | : (make-overlapped) ( -- overlapped-ext )
 | 
					
						
							|  |  |  |     OVERLAPPED malloc-struct &free ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | : make-overlapped ( port -- overlapped-ext )
 | 
					
						
							|  |  |  |     [ (make-overlapped) ] dip
 | 
					
						
							| 
									
										
										
										
											2011-10-07 18:04:00 -04:00
										 |  |  |     handle>> ptr>> [ | 
					
						
							|  |  |  |         [ 32 bits >>offset ] | 
					
						
							|  |  |  |         [ -32 shift >>offset-high ] bi
 | 
					
						
							|  |  |  |     ] when* ;
 | 
					
						
							| 
									
										
										
										
											2010-09-19 15:02:32 -04:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-09-18 21:25:06 -04:00
										 |  |  | M: windows FileArgs-overlapped ( port -- overlapped )
 | 
					
						
							| 
									
										
										
										
											2010-09-19 15:02:32 -04:00
										 |  |  |     make-overlapped ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | : <completion-port> ( handle existing -- handle )
 | 
					
						
							|  |  |  |      f 1 CreateIoCompletionPort dup win32-error=0/f ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | SYMBOL: master-completion-port | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | : <master-completion-port> ( -- handle )
 | 
					
						
							|  |  |  |     INVALID_HANDLE_VALUE f <completion-port> ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-09-18 21:25:06 -04:00
										 |  |  | M: windows add-completion ( win32-handle -- win32-handle )
 | 
					
						
							| 
									
										
										
										
											2010-09-19 15:02:32 -04:00
										 |  |  |     dup handle>> master-completion-port get-global <completion-port> drop ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | : eof? ( error -- ? )
 | 
					
						
							|  |  |  |     { [ ERROR_HANDLE_EOF = ] [ ERROR_BROKEN_PIPE = ] } 1|| ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | : twiddle-thumbs ( overlapped port -- bytes-transferred )
 | 
					
						
							|  |  |  |     [ | 
					
						
							|  |  |  |         drop
 | 
					
						
							|  |  |  |         [ self ] dip >c-ptr pending-overlapped get-global set-at
 | 
					
						
							|  |  |  |         "I/O" suspend { | 
					
						
							|  |  |  |             { [ dup integer? ] [ ] } | 
					
						
							|  |  |  |             { [ dup array? ] [ | 
					
						
							|  |  |  |                 first dup eof? | 
					
						
							|  |  |  |                 [ drop 0 ] [ n>win32-error-string throw ] if
 | 
					
						
							|  |  |  |             ] } | 
					
						
							|  |  |  |         } cond
 | 
					
						
							|  |  |  |     ] with-timeout ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | :: wait-for-overlapped ( nanos -- bytes-transferred overlapped error? )
 | 
					
						
							|  |  |  |     nanos [ 1,000,000 /i ] [ INFINITE ] if* :> timeout | 
					
						
							|  |  |  |     master-completion-port get-global
 | 
					
						
							|  |  |  |     { int void* pointer: OVERLAPPED } | 
					
						
							|  |  |  |     [ timeout GetQueuedCompletionStatus zero? ] with-out-parameters | 
					
						
							|  |  |  |     :> ( error? bytes key overlapped )
 | 
					
						
							|  |  |  |     bytes overlapped error? ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | : resume-callback ( result overlapped -- )
 | 
					
						
							|  |  |  |     >c-ptr pending-overlapped get-global delete-at* drop resume-with ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | : handle-overlapped ( nanos -- ? )
 | 
					
						
							|  |  |  |     wait-for-overlapped [ | 
					
						
							|  |  |  |         [ | 
					
						
							|  |  |  |             [ drop GetLastError 1array ] dip resume-callback t
 | 
					
						
							|  |  |  |         ] [ drop f ] if*
 | 
					
						
							|  |  |  |     ] [ resume-callback t ] if ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | M: win32-handle cancel-operation | 
					
						
							|  |  |  |     [ handle>> CancelIo win32-error=0/f ] unless-disposed ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-09-18 21:25:06 -04:00
										 |  |  | M: windows io-multiplex ( nanos -- )
 | 
					
						
							| 
									
										
										
										
											2010-09-19 15:02:32 -04:00
										 |  |  |     handle-overlapped [ 0 io-multiplex ] when ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-09-18 21:25:06 -04:00
										 |  |  | M: windows init-io ( -- )
 | 
					
						
							| 
									
										
										
										
											2010-09-19 15:02:32 -04:00
										 |  |  |     <master-completion-port> master-completion-port set-global
 | 
					
						
							|  |  |  |     H{ } clone pending-overlapped set-global ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | ERROR: invalid-file-size n ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-10-19 13:15:09 -04:00
										 |  |  | : (handle>file-size) ( handle -- n/f )
 | 
					
						
							|  |  |  |     0 ulonglong <ref> [ GetFileSizeEx ] keep swap
 | 
					
						
							|  |  |  |     [ drop f ] [ drop ulonglong deref ] if-zero ;
 | 
					
						
							| 
									
										
										
										
											2010-09-19 15:02:32 -04:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-10-19 13:15:09 -04:00
										 |  |  | ! GetFileSizeEx errors with ERROR_INVALID_FUNCTION if handle is not seekable | 
					
						
							| 
									
										
										
										
											2011-10-19 04:16:53 -04:00
										 |  |  | : handle>file-size ( handle -- n/f )
 | 
					
						
							| 
									
										
										
										
											2011-10-19 13:15:09 -04:00
										 |  |  |     (handle>file-size) [ | 
					
						
							|  |  |  |         GetLastError ERROR_INVALID_FUNCTION =
 | 
					
						
							|  |  |  |         [ f ] [ throw-win32-error ] if
 | 
					
						
							|  |  |  |     ] unless* ;
 | 
					
						
							|  |  |  |      | 
					
						
							| 
									
										
										
										
											2010-09-19 15:02:32 -04:00
										 |  |  | ERROR: seek-before-start n ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | : set-seek-ptr ( n handle -- )
 | 
					
						
							|  |  |  |     [ dup 0 < [ seek-before-start ] when ] dip ptr<< ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-09-18 21:25:06 -04:00
										 |  |  | M: windows tell-handle ( handle -- n ) ptr>> ;
 | 
					
						
							| 
									
										
										
										
											2010-09-19 15:02:32 -04:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-09-18 21:25:06 -04:00
										 |  |  | M: windows seek-handle ( n seek-type handle -- )
 | 
					
						
							| 
									
										
										
										
											2010-09-19 15:02:32 -04:00
										 |  |  |     swap { | 
					
						
							|  |  |  |         { seek-absolute [ set-seek-ptr ] } | 
					
						
							|  |  |  |         { seek-relative [ [ ptr>> + ] keep set-seek-ptr ] } | 
					
						
							|  |  |  |         { seek-end [ [ handle>> handle>file-size + ] keep set-seek-ptr ] } | 
					
						
							|  |  |  |         [ bad-seek-type ] | 
					
						
							|  |  |  |     } case ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-10-14 22:14:59 -04:00
										 |  |  | M: windows can-seek-handle? ( handle -- ? )
 | 
					
						
							| 
									
										
										
										
											2011-10-19 04:16:53 -04:00
										 |  |  |     handle>> handle>file-size >boolean ;
 | 
					
						
							| 
									
										
										
										
											2011-10-14 22:14:59 -04:00
										 |  |  | 
 | 
					
						
							|  |  |  | M: windows handle-length ( handle -- n/f )
 | 
					
						
							| 
									
										
										
										
											2011-10-19 04:16:53 -04:00
										 |  |  |     handle>> handle>file-size | 
					
						
							|  |  |  |     dup { 0 f } member? [ drop f ] when ;
 | 
					
						
							| 
									
										
										
										
											2011-10-14 22:14:59 -04:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2010-09-19 15:02:32 -04:00
										 |  |  | : file-error? ( n -- eof? )
 | 
					
						
							|  |  |  |     zero? [ | 
					
						
							|  |  |  |         GetLastError { | 
					
						
							|  |  |  |             { [ dup expected-io-error? ] [ drop f ] } | 
					
						
							|  |  |  |             { [ dup eof? ] [ drop t ] } | 
					
						
							|  |  |  |             [ n>win32-error-string throw ] | 
					
						
							|  |  |  |         } cond
 | 
					
						
							|  |  |  |     ] [ f ] if ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | : wait-for-file ( FileArgs n port -- n )
 | 
					
						
							|  |  |  |     swap file-error? | 
					
						
							|  |  |  |     [ 2drop 0 ] [ [ lpOverlapped>> ] dip twiddle-thumbs ] if ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | : update-file-ptr ( n port -- )
 | 
					
						
							|  |  |  |     handle>> dup ptr>> [ rot + >>ptr drop ] [ 2drop ] if* ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | : finish-write ( n port -- )
 | 
					
						
							|  |  |  |     [ update-file-ptr ] [ buffer>> buffer-consume ] 2bi ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | : setup-read ( <FileArgs> -- hFile lpBuffer nNumberOfBytesToRead lpNumberOfBytesRead lpOverlapped )
 | 
					
						
							|  |  |  |     { | 
					
						
							|  |  |  |         [ hFile>> ] | 
					
						
							|  |  |  |         [ lpBuffer>> buffer-end ] | 
					
						
							|  |  |  |         [ lpBuffer>> buffer-capacity ] | 
					
						
							|  |  |  |         [ lpNumberOfBytesRet>> ] | 
					
						
							|  |  |  |         [ lpOverlapped>> ] | 
					
						
							|  |  |  |     } cleave ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | : setup-write ( <FileArgs> -- hFile lpBuffer nNumberOfBytesToWrite lpNumberOfBytesWritten lpOverlapped )
 | 
					
						
							|  |  |  |     { | 
					
						
							|  |  |  |         [ hFile>> ] | 
					
						
							|  |  |  |         [ lpBuffer>> buffer@ ] | 
					
						
							|  |  |  |         [ lpBuffer>> buffer-length ] | 
					
						
							|  |  |  |         [ lpNumberOfBytesRet>> ] | 
					
						
							|  |  |  |         [ lpOverlapped>> ] | 
					
						
							|  |  |  |     } cleave ;
 | 
					
						
							|  |  |  |      | 
					
						
							| 
									
										
										
										
											2011-09-18 21:25:06 -04:00
										 |  |  | M: windows (wait-to-write) | 
					
						
							| 
									
										
										
										
											2010-09-19 15:02:32 -04:00
										 |  |  |     [ | 
					
						
							|  |  |  |         [ make-FileArgs dup setup-write WriteFile ] | 
					
						
							|  |  |  |         [ wait-for-file ] | 
					
						
							|  |  |  |         [ finish-write ] | 
					
						
							|  |  |  |         tri
 | 
					
						
							|  |  |  |     ] with-destructors ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | : finish-read ( n port -- )
 | 
					
						
							|  |  |  |     [ update-file-ptr ] [ buffer>> n>buffer ] 2bi ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-09-18 21:25:06 -04:00
										 |  |  | M: windows (wait-to-read) ( port -- )
 | 
					
						
							| 
									
										
										
										
											2010-09-19 15:02:32 -04:00
										 |  |  |     [ | 
					
						
							|  |  |  |         [ make-FileArgs dup setup-read ReadFile ] | 
					
						
							|  |  |  |         [ wait-for-file ] | 
					
						
							|  |  |  |         [ finish-read ] | 
					
						
							|  |  |  |         tri
 | 
					
						
							|  |  |  |     ] with-destructors ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | : console-app? ( -- ? ) GetConsoleWindow >boolean ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-09-18 21:25:06 -04:00
										 |  |  | M: windows init-stdio | 
					
						
							| 
									
										
										
										
											2010-09-19 15:02:32 -04:00
										 |  |  |     console-app? | 
					
						
							|  |  |  |     [ init-c-stdio ] | 
					
						
							|  |  |  |     [ null-reader null-writer null-writer set-stdio ] if ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2008-12-15 02:32:21 -05:00
										 |  |  | : open-file ( path access-mode create-mode flags -- handle )
 | 
					
						
							|  |  |  |     [ | 
					
						
							|  |  |  |         [ share-mode default-security-attributes ] 2dip
 | 
					
						
							|  |  |  |         CreateFile-flags f CreateFile opened-file | 
					
						
							|  |  |  |     ] with-destructors ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2009-01-13 19:57:09 -05:00
										 |  |  | : open-r/w ( path -- win32-file )
 | 
					
						
							| 
									
										
										
										
											2010-04-01 15:43:27 -04:00
										 |  |  |     flags{ GENERIC_READ GENERIC_WRITE } | 
					
						
							| 
									
										
										
										
											2008-12-15 02:32:21 -05:00
										 |  |  |     OPEN_EXISTING 0 open-file ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | : open-read ( path -- win32-file )
 | 
					
						
							|  |  |  |     GENERIC_READ OPEN_EXISTING 0 open-file 0 >>ptr ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | : open-write ( path -- win32-file )
 | 
					
						
							|  |  |  |     GENERIC_WRITE CREATE_ALWAYS 0 open-file 0 >>ptr ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | : (open-append) ( path -- win32-file )
 | 
					
						
							|  |  |  |     GENERIC_WRITE OPEN_ALWAYS 0 open-file ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | : open-existing ( path -- win32-file )
 | 
					
						
							| 
									
										
										
										
											2010-04-01 15:43:27 -04:00
										 |  |  |     flags{ GENERIC_READ GENERIC_WRITE } | 
					
						
							| 
									
										
										
										
											2008-12-15 02:32:21 -05:00
										 |  |  |     share-mode | 
					
						
							|  |  |  |     f
 | 
					
						
							|  |  |  |     OPEN_EXISTING | 
					
						
							|  |  |  |     FILE_FLAG_BACKUP_SEMANTICS | 
					
						
							|  |  |  |     f CreateFileW dup win32-error=0/f <win32-file> ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | : maybe-create-file ( path -- win32-file ? )
 | 
					
						
							|  |  |  |     #! return true if file was just created | 
					
						
							| 
									
										
										
										
											2010-04-01 15:43:27 -04:00
										 |  |  |     flags{ GENERIC_READ GENERIC_WRITE } | 
					
						
							| 
									
										
										
										
											2008-12-15 02:32:21 -05:00
										 |  |  |     share-mode | 
					
						
							|  |  |  |     f
 | 
					
						
							|  |  |  |     OPEN_ALWAYS | 
					
						
							|  |  |  |     0 CreateFile-flags | 
					
						
							|  |  |  |     f CreateFileW dup win32-error=0/f <win32-file> | 
					
						
							|  |  |  |     GetLastError ERROR_ALREADY_EXISTS = not ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | : set-file-pointer ( handle length method -- )
 | 
					
						
							| 
									
										
										
										
											2010-10-20 18:42:53 -04:00
										 |  |  |     [ [ handle>> ] dip d>w/w uint <ref> ] dip SetFilePointer | 
					
						
							| 
									
										
										
										
											2009-08-18 04:46:46 -04:00
										 |  |  |     INVALID_SET_FILE_POINTER = [ "SetFilePointer failed" throw ] when ;
 | 
					
						
							| 
									
										
										
										
											2008-12-15 02:32:21 -05:00
										 |  |  | 
 | 
					
						
							|  |  |  | M: windows (file-reader) ( path -- stream )
 | 
					
						
							|  |  |  |     open-read <input-port> ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | M: windows (file-writer) ( path -- stream )
 | 
					
						
							|  |  |  |     open-write <output-port> ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | M: windows (file-appender) ( path -- stream )
 | 
					
						
							|  |  |  |     open-append <output-port> ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | SYMBOLS: +read-only+ +hidden+ +system+ | 
					
						
							|  |  |  | +archive+ +device+ +normal+ +temporary+ | 
					
						
							|  |  |  | +sparse-file+ +reparse-point+ +compressed+ +offline+ | 
					
						
							|  |  |  | +not-content-indexed+ +encrypted+ ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-10-19 06:14:19 -04:00
										 |  |  | SLOT: attributes | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-10-19 05:31:48 -04:00
										 |  |  | : read-only? ( file-info -- ? )
 | 
					
						
							|  |  |  |     attributes>> +read-only+ swap member? ;
 | 
					
						
							|  |  |  |      | 
					
						
							|  |  |  | : set-file-attributes ( path flags -- )
 | 
					
						
							|  |  |  |     SetFileAttributes win32-error=0/f ;
 | 
					
						
							|  |  |  |      | 
					
						
							|  |  |  | : set-file-normal-attribute ( path -- )
 | 
					
						
							|  |  |  |     FILE_ATTRIBUTE_NORMAL set-file-attributes ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2010-09-17 15:19:10 -04:00
										 |  |  | : win32-file-attribute ( n symbol attr -- )
 | 
					
						
							| 
									
										
										
										
											2008-12-15 02:32:21 -05:00
										 |  |  |     rot mask? [ , ] [ drop ] if ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | : win32-file-attributes ( n -- seq )
 | 
					
						
							|  |  |  |     [ | 
					
						
							|  |  |  |         { | 
					
						
							|  |  |  |             [ +read-only+ FILE_ATTRIBUTE_READONLY win32-file-attribute ] | 
					
						
							|  |  |  |             [ +hidden+ FILE_ATTRIBUTE_HIDDEN win32-file-attribute ] | 
					
						
							|  |  |  |             [ +system+ FILE_ATTRIBUTE_SYSTEM win32-file-attribute ] | 
					
						
							|  |  |  |             [ +directory+ FILE_ATTRIBUTE_DIRECTORY win32-file-attribute ] | 
					
						
							|  |  |  |             [ +archive+ FILE_ATTRIBUTE_ARCHIVE win32-file-attribute ] | 
					
						
							|  |  |  |             [ +device+ FILE_ATTRIBUTE_DEVICE win32-file-attribute ] | 
					
						
							|  |  |  |             [ +normal+ FILE_ATTRIBUTE_NORMAL win32-file-attribute ] | 
					
						
							|  |  |  |             [ +temporary+ FILE_ATTRIBUTE_TEMPORARY win32-file-attribute ] | 
					
						
							|  |  |  |             [ +sparse-file+ FILE_ATTRIBUTE_SPARSE_FILE win32-file-attribute ] | 
					
						
							|  |  |  |             [ +reparse-point+ FILE_ATTRIBUTE_REPARSE_POINT win32-file-attribute ] | 
					
						
							|  |  |  |             [ +compressed+ FILE_ATTRIBUTE_COMPRESSED win32-file-attribute ] | 
					
						
							|  |  |  |             [ +offline+ FILE_ATTRIBUTE_OFFLINE win32-file-attribute ] | 
					
						
							|  |  |  |             [ +not-content-indexed+ FILE_ATTRIBUTE_NOT_CONTENT_INDEXED win32-file-attribute ] | 
					
						
							|  |  |  |             [ +encrypted+ FILE_ATTRIBUTE_ENCRYPTED win32-file-attribute ] | 
					
						
							|  |  |  |         } cleave
 | 
					
						
							|  |  |  |     ] { } make ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | : win32-file-type ( n -- symbol )
 | 
					
						
							|  |  |  |     FILE_ATTRIBUTE_DIRECTORY mask? +directory+ +regular-file+ ? ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | : (set-file-times) ( handle timestamp/f timestamp/f timestamp/f -- )
 | 
					
						
							|  |  |  |     [ timestamp>FILETIME ] tri@
 | 
					
						
							|  |  |  |     SetFileTime win32-error=0/f ;
 | 
					
						
							| 
									
										
										
										
											2010-09-17 15:19:10 -04:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-09-18 21:25:06 -04:00
										 |  |  | M: windows cwd | 
					
						
							| 
									
										
										
										
											2011-09-25 14:49:27 -04:00
										 |  |  |     MAX_UNICODE_PATH dup ushort <c-array> | 
					
						
							| 
									
										
										
										
											2012-06-21 11:32:53 -04:00
										 |  |  |     [ GetCurrentDirectory win32-error=0/f ] keep alien>native-string ;
 | 
					
						
							| 
									
										
										
										
											2010-09-19 15:02:32 -04:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-09-18 21:25:06 -04:00
										 |  |  | M: windows cd | 
					
						
							| 
									
										
										
										
											2010-09-19 15:02:32 -04:00
										 |  |  |     SetCurrentDirectory win32-error=0/f ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | CONSTANT: unicode-prefix "\\\\?\\" | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-09-18 21:25:06 -04:00
										 |  |  | M: windows root-directory? ( path -- ? )
 | 
					
						
							| 
									
										
										
										
											2010-09-19 15:02:32 -04:00
										 |  |  |     { | 
					
						
							|  |  |  |         { [ dup empty? ] [ drop f ] } | 
					
						
							|  |  |  |         { [ dup [ path-separator? ] all? ] [ drop t ] } | 
					
						
							|  |  |  |         { [ dup trim-tail-separators { [ length 2 = ] | 
					
						
							|  |  |  |           [ second CHAR: : = ] } 1&& ] [ drop t ] } | 
					
						
							|  |  |  |         { [ dup unicode-prefix head? ] | 
					
						
							|  |  |  |           [ trim-tail-separators length unicode-prefix length 2 + = ] } | 
					
						
							|  |  |  |         [ drop f ] | 
					
						
							|  |  |  |     } cond ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | : prepend-prefix ( string -- string' )
 | 
					
						
							|  |  |  |     dup unicode-prefix head? [ | 
					
						
							|  |  |  |         unicode-prefix prepend
 | 
					
						
							|  |  |  |     ] unless ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | TR: normalize-separators "/" "\\" ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-08-28 15:55:09 -04:00
										 |  |  | <PRIVATE
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | : unc-path? ( string -- ? )
 | 
					
						
							|  |  |  |     [ "//" head? ] [ "\\\\" head? ] bi or ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | PRIVATE>
 | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-09-18 21:25:06 -04:00
										 |  |  | M: windows normalize-path ( string -- string' )
 | 
					
						
							| 
									
										
										
										
											2011-08-28 15:55:09 -04:00
										 |  |  |     dup unc-path? [ | 
					
						
							| 
									
										
										
										
											2011-01-25 07:32:21 -05:00
										 |  |  |         normalize-separators | 
					
						
							|  |  |  |     ] [ | 
					
						
							|  |  |  |         absolute-path | 
					
						
							|  |  |  |         normalize-separators | 
					
						
							|  |  |  |         prepend-prefix | 
					
						
							|  |  |  |     ] if ;
 | 
					
						
							| 
									
										
										
										
											2010-09-19 15:02:32 -04:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-09-18 21:25:06 -04:00
										 |  |  | M: windows CreateFile-flags ( DWORD -- DWORD )
 | 
					
						
							| 
									
										
										
										
											2010-09-19 15:02:32 -04:00
										 |  |  |     FILE_FLAG_OVERLAPPED bitor ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | <PRIVATE
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | : windows-file-size ( path -- size )
 | 
					
						
							|  |  |  |     normalize-path 0 WIN32_FILE_ATTRIBUTE_DATA <struct> | 
					
						
							|  |  |  |     [ GetFileAttributesEx win32-error=0/f ] keep
 | 
					
						
							|  |  |  |     [ nFileSizeLow>> ] [ nFileSizeHigh>> ] bi >64bit ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | PRIVATE>
 | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-09-18 21:25:06 -04:00
										 |  |  | M: windows open-append | 
					
						
							| 
									
										
										
										
											2010-09-19 15:02:32 -04:00
										 |  |  |     [ dup windows-file-size ] [ drop 0 ] recover
 | 
					
						
							|  |  |  |     [ (open-append) ] dip >>ptr ;
 | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2011-09-18 21:25:06 -04:00
										 |  |  | M: windows home | 
					
						
							| 
									
										
										
										
											2010-09-19 15:02:32 -04:00
										 |  |  |     { | 
					
						
							|  |  |  |         [ "HOMEDRIVE" os-env "HOMEPATH" os-env append-path ] | 
					
						
							|  |  |  |         [ "USERPROFILE" os-env ] | 
					
						
							|  |  |  |         [ my-documents ] | 
					
						
							| 
									
										
										
										
											2010-10-20 18:42:53 -04:00
										 |  |  |     } 0|| ;
 |