@@ -8,15 +8,12 @@ use std::mem;
8
8
use std:: os:: raw:: c_void;
9
9
use std:: os:: windows:: ffi:: OsStrExt ;
10
10
use std:: os:: windows:: io:: AsRawHandle ;
11
- use std:: slice;
12
11
use std:: { char, mem:: MaybeUninit } ;
13
12
14
13
use encode_unicode:: error:: InvalidUtf16Tuple ;
15
14
use encode_unicode:: CharExt ;
16
15
use windows_sys:: Win32 :: Foundation :: { HANDLE , INVALID_HANDLE_VALUE , MAX_PATH } ;
17
- use windows_sys:: Win32 :: Storage :: FileSystem :: {
18
- FileNameInfo , GetFileInformationByHandleEx , FILE_NAME_INFO ,
19
- } ;
16
+ use windows_sys:: Win32 :: Storage :: FileSystem :: { FileNameInfo , GetFileInformationByHandleEx } ;
20
17
use windows_sys:: Win32 :: System :: Console :: {
21
18
FillConsoleOutputAttribute , FillConsoleOutputCharacterA , GetConsoleCursorInfo , GetConsoleMode ,
22
19
GetConsoleScreenBufferInfo , GetNumberOfConsoleInputEvents , GetStdHandle , ReadConsoleInputW ,
@@ -527,22 +524,37 @@ pub fn msys_tty_on(term: &Term) -> bool {
527
524
}
528
525
}
529
526
530
- let size = mem:: size_of :: < FILE_NAME_INFO > ( ) ;
531
- let mut name_info_bytes = vec ! [ 0u8 ; size + MAX_PATH as usize * mem:: size_of:: <u16 >( ) ] ;
527
+ /// Mirrors windows_sys::Win32::Storage::FileSystem::FILE_NAME_INFO, giving
528
+ /// it a fixed length that we can stack allocate
529
+ #[ repr( C ) ]
530
+ #[ allow( non_snake_case) ]
531
+ struct FILE_NAME_INFO {
532
+ FileNameLength : u32 ,
533
+ FileName : [ u16 ; MAX_PATH as usize ] ,
534
+ }
535
+
536
+ let mut name_info = FILE_NAME_INFO {
537
+ FileNameLength : 0 ,
538
+ FileName : [ 0 ; MAX_PATH as usize ] ,
539
+ } ;
532
540
let res = GetFileInformationByHandleEx (
533
541
handle as HANDLE ,
534
542
FileNameInfo ,
535
- & mut * name_info_bytes as * mut _ as * mut c_void ,
536
- name_info_bytes . len ( ) as u32 ,
543
+ & mut name_info as * mut _ as * mut c_void ,
544
+ std :: mem :: size_of :: < FILE_NAME_INFO > ( ) as u32 ,
537
545
) ;
538
546
if res == 0 {
539
547
return false ;
540
548
}
541
- let name_info: & FILE_NAME_INFO = & * ( name_info_bytes. as_ptr ( ) as * const FILE_NAME_INFO ) ;
542
- let s = slice:: from_raw_parts (
543
- name_info. FileName . as_ptr ( ) ,
544
- name_info. FileNameLength as usize / 2 ,
545
- ) ;
549
+
550
+ // Use `get` because `FileNameLength` can be out of range.
551
+ let s = match name_info
552
+ . FileName
553
+ . get ( ..name_info. FileNameLength as usize / 2 )
554
+ {
555
+ Some ( s) => s,
556
+ None => return false ,
557
+ } ;
546
558
let name = String :: from_utf16_lossy ( s) ;
547
559
// This checks whether 'pty' exists in the file name, which indicates that
548
560
// a pseudo-terminal is attached. To mitigate against false positives
0 commit comments