We help IT Professionals succeed at work.

Check out our new AWS podcast with Certified Expert, Phil Phillips! Listen to "How to Execute a Seamless AWS Migration" on EE or on your favorite podcast platform. Listen Now

x

Monitoring file names

antony061897
antony061897 asked
on
Medium Priority
349 Views
Last Modified: 2010-05-03
All my users are policy edited and although they can only run a list of given programs they are getting around this by renaming setup.exe to calc.exe for example.

Is there anyway I can monitor and stop the renaming of given file names?

Perhaps a small vb program sitting in memory constanly monitoring the situation?


Any help appreciated.


Antony
Comment
Watch Question

Commented:
You might try comparing the executable name with it's known file size.
Top Expert 2009

Commented:
Some, but not all programs have version-information included. One of the parts of the version-information is usually the "Origianal filename". I suggest that you make a small program which will be called everytime a user starts a program and checks if the internal "Original filename" matches the filename on the commandline.

If you want to know how to do this within VB or C/C++ I'll be happy to help you further.

Regards, Abel

BTW. There's also a way of controlling changing names in the shell. You need some api-calls for it that (as far as I know) cannot be implemented in VB but CAN be called from C/C++. Let me know if you want it this other way, but you'll need to know how to program in C/C++.
Top Expert 2009

Commented:
Sorry, maybe the other way can be done in VB as well. You should take a look at FindFirstChangeNotification with the FILE_NOTIFY_CHANGE_FILE_NAME flag. You will get a handle to an object that will be set to signaled state whenever a file changes. I never tried the function WaitForSingleObject in VB, but that's the one you should use to let your app (or a specific thread) wait till a file is being changed.

Commented:
If your users are logging on somewhere for you to identify them as "policy edited", e.g.,  you can look at their signature at the beginning of each of your apps and throw out those who don't belong.
 

Commented:
antony,

  If App.EXEName <> "myName" Then
    MsgBox "Do not rename me"
    End
  End If

Regards
Top Expert 2009

Commented:
Soeding,
where is the monitoring part? And why app.exe? That's the name of your own app, not the app that's started by the user. I think Antony wants a monitoring program which limits renaming of certain executable files - a so called policy-program.
Top Expert 2009

Commented:
If I'm mistaken, please accept my appologies... :-)
Regards, Abel

Author

Commented:
Thanks for your comments so far.

Abel is indeed correct - I need to stop users running or renaming certain executables.

Abel, could you expand a little on how I would proceed.

Antony

Commented:
I am also interessed in knowing a way to that in VB
Top Expert 2009

Commented:
I can give you source in C in one or two days (not counting the weekend). Are you able to read C and/or translate it to VB? Usually I can get things easiliy ported for people here asking (very) difficult questions (which can be done in VB, but easier in C), but I've never tried WaitForSingleObject in VB. If I find the time I'll try it out in VB as well and let you know, if not, I'll at least give you the declarations you need and some pseudocode (and the source of C), allright?

You'll have to reopen for me to answer this q.

Regards, Abel

Author

Commented:
Perhaps a different approach whould be a program which looks for a certain word within all open/active windows

How would I get the names of all open windows

and how would I close that window?

Antony

Commented:
There is no problem if you send me the source in C, I will try to translate in VB.
Top Expert 2009

Commented:
Isn't this the question of Antony?
I would like to send it to him, if he/she has no problem with it.

Antony,
I don't understand your goal when you say "looking for a word withing all open active windows". Do you mean that the filenames appear in de caption of a window and that you want to catch that? That's quite easy to implement. If you really want to do it that way, say so in your comment. Also say what "word" you're trying to find. It's quite easy to close windows. Use FindWindow to get a handle to the specific window. Use DestroyWindow(hWnd) to destroy the window.

Notify here about what approach you need and I help you further with it.

Author

Commented:
I really would like to approach the situation 2 ways:

1. stop users renaming certain file names.

2. stop users exectuting certain file names.

When I said looking for a word - I should have said looking for a string match within the <windowname>.caption

Code for this would also be handy.

Antony

Author

Commented:
Example 'words' would be setup, install etc.

Antony
Top Expert 2009

Commented:
This evening (my evening, it's 15.45), I can give you something to work with. I have enough info, I think to give you a proper solution.
What about C?

Abel

Author

Commented:
VB would be a better answer, as I don't have any C development tools.

Sorry.

I do appreciated all the attention your showing to my problem.

BTW, I'm in the UK timezone.

Antony
Top Expert 2009

Commented:
That's only an hour earlier. I'm from the European Common Timezone, if it's called that way. (just from Holland, actually).

Commented:
Could you simply make the setup file hidden, Read only, System type so they can't find the file.......
It may seem simple but It may stop them...

Commented:
You can make a program that runs in the background and uses FindWindow to search the system for the window captions of the programs you do not want the users to run (such as "The Microsoft Hearts Network"). The monitoring program would use a timer and call FindWindow every minute or so. As soon as it finds the window, it will DestroyWindow it, or post WM_QUIT to it, or do something of the sort to close the application. Since you are using window captions of the apps instead of filenames, the only way the users will be able to run the apps will be to hexedit them (to change the captions) or to disable your monitoring program.

Author

Commented:
That all sounds good, but is there a way of retrieving the windows names so I can filter them for certain words?

BTW, i tried FindWindow and DestroyWindow but DestroyWindow didn't work, even though the handle was correct, I tried CloseWindow and CloseHandle too.

Antony
Top Expert 2009

Commented:
WM_QUIT is actually a better way to destroy a window. A window created by a differrent thread than your own cannot be destroyed by using DestroyWindow.
Most windows have a different caption. It's easier to monitor the filename changes, because you might get a huge database in the end with all the windowcaptions you ever encountered in it. And every new kind of setup-program (or perhaps other programs you want to restrict access to) might have other captions.
BTW Monitoring every minute or so, sounds fine, but if someone is fast enough with clicking the "next" button in a setup program the caption may be changed already.

And what about users who end your monitoring program (via Ctrl-Alt-Del)?

I still think the best way is using the monitoring filenames - way. It's a bit more work, but also more difficult to get around.

Regards, Abel
Top Expert 2009

Commented:
errh... how can I post earlier than you, Anthony? You were already in the thread.

Commented:
Hmmm, apparently my comment got erased. Basically, you can use EnumWindows to have the system give you a handle to every open window. Then, you can scan the captions for keywords and WM_QUIT them if neccesary.

Commented:
It seems to me that you're trying to apply a technology solution to what is basically a personnel problem.

If it's REALLY important that people not run certain software, then get management concurrence to take it off their machines, and threaten them with termination of employment if they're caught violating company policy. If management won't do that, then it's probably not important enough for you to worry about, either.

Computers are very good at some things, and totally inappropriate for others. Part of our jobs, as systems professionals, is to recognize the difference.

Author

Commented:
Sinclair,

Could you tell me how to use EnumWindows - Is there such a declare?

Antony
Top Expert 2009

Commented:
I hope Sinclair doesn't mind me answering this. Sorry, I just couldn't resist. Here are the declarations of the functions. Below are the explanations of them. It's strange that these declarations are not in the API-viewer, but I converted the C-declaration for you.

'EnumWindow API
Declare Function EnumWindows Lib "user32" Alias "EnumWindows" (ByVal lpEnumFunc As Long, ByVal lParam As Long) As Long

'EnumWindowsProc declare. Use it with AddressOf
Declare Function EnumWindowsProc (ByVal hWnd As Long, ByVal lParam As Long) As Long


EnumWindows uses an application defined callback function. The declare of EnumWindowsProc is of the form the function should have. When you call EnumWindows, call it like this:
EnumWindows(AddressOf(EnumWindowsProc), SomeValue)

The lParam (here: SomeValue) will be passed to you callback function. You can (but don't have to) use it as identification parameter or something like that. When you call EnumWindows, this is what happens:
1. EnumWindows starts enumerating the top level windows
2. It passes every value hWnd value it finds to EnumWindowsProc
3. It will continue searching untill all windows are found or EnumWindowsProc returns false.

Your EnumWindowsProc can look something like this:

Function EnumWindowsProc (ByVal hWnd As Long, ByVal lParam As Long) As Long

Dim txt As String * MAX_PATH

GetWindowText(hWnd, txt, MAX_PATH)
If Instr(1, txt, "Setup") > 0 then
    SendMessage(hWnd, WM_QUIT, 0, 0)
    MsgBox "You are not allowed to run that program!"
End If
EnumWindowsProc = True

End Function


Declarations of GetWindowText and SendMessage can be found in the API-viewer. Below, for your convenience, the MS SDK reference of EnumWindows and EnumWindowsProc:


EnumWindows  

The EnumWindows function enumerates all top-level windows on the screen by passing the handle of each window, in turn, to an application-defined callback function. EnumWindows continues until the last top-level window is enumerated or the callback function returns FALSE.

BOOL EnumWindows(
    WNDENUMPROC lpEnumFunc,  // pointer to callback function
    LPARAM lParam            // application-defined value
);
 


Parameters

lpEnumFunc
Points to an application-defined callback function. For more information, see the EnumWindowsProc callback function.

lParam
Specifies a 32-bit, application-defined value to be passed to the callback function.

Return Values
If the function succeeds, the return value is nonzero.
If the function fails, the return value is zero.

Remarks
The EnumWindows function does not enumerate child windows.
This function is more reliable than calling the GetWindow function in a loop. An application that calls GetWindow to perform this task risks being caught in an infinite loop or referencing a handle to a window that has been destroyed.


********************************************************************************************

EnumWindowsProc  

The EnumWindowsProc function is an application-defined callback function that receives top-level window handles as a result of a call to the EnumWindows or EnumDesktopWindows function.

BOOL CALLBACK EnumWindowsProc(
    HWND hwnd,          // handle to parent window
    LPARAM lParam     // application-defined value
);
 


Parameters

hwnd
Identifies a top-level window.

lParam
Specifies the application-defined value given in EnumWindows or EnumDesktopWindows.

Return Values
To continue enumeration, the callback function must return TRUE; to stop enumeration, it must return FALSE.

Remarks
The callback function can perform any desired task.

An application must register this callback function by passing its address to EnumWindows or EnumDesktopWindows. EnumWindowsProc is a placeholder for the application-defined function name. The WNDENUMPROC type is a pointer to an EnumWindowsProc function.


Hope this helps you further. When you need more info, let me know. BTW, no FindFirstChangeNotification anymore?

Regards, Abel

Author

Commented:
Thanks!

So that's why I could find enumwin!

Now to cut'n'paste :)

Antony

Author

Commented:
Ok, I've got your code working great...

But, now I can't find any reference to WM_QUIT anywhere

Looking good Abel - thanks.
BTW, I haven't given up on FindFirstChangeNotification just need to work out how to use it in VB. - Must learn C/C++

Antony.

Author

Commented:
The SendMessage(hWnd, WM_QUIT, 0, 0) part doesn't work in VB5

Is there a VB5 equiv of SendMessage?

Antony

Author

Commented:
Don't worry - I've found it - it's an API - stupid me

Antony

Author

Commented:
I still can't get SendMessage to kill any window, this is the code I have so far:

Declare Function EnumWindows Lib "user32" (ByVal lpEnumFunc As Long, ByVal lParam As Long) As Long

Declare Function GetWindowText Lib "user32" Alias "GetWindowTextA" (ByVal hwnd As Long, ByVal lpString As String, ByVal cch As Long) As Long

Declare Function SendMessage Lib "user32" Alias "SendMessageA" (ByVal hwnd As Long, ByVal wMsg As Long, ByVal wParam As Long, lParam As Any) As Long

Function EnumWindowsProc(ByVal hwnd As Long, ByVal lParam As Long) As Long

----------------------------

Dim txt As String * 255

GetWindowText hwnd, txt, 255

Debug.Print hwnd, txt

If InStr(1, txt, "Extractor", vbTextCompare) > 0 Then
    SendMessage hwnd, &H12, 0, 0
    MsgBox "You do not have permission to run:" & Chr$(10) & Chr$(10) & txt, vbCritical + vbOKOnly, "Error"
End If

EnumWindowsProc = True

End Function

-------------------------

What am I doing wrong?

Antony
Top Expert 2009

Commented:
Try using PostMessage in stead of SendMessage with WM_QUIT when you want an application to quit. Perhaps it's even a better idea to try SendMessage(hWnd, WM_CLOSE, 0, 0) to the window. I investigated a bit more, and it turned out that that is the first thing to send to a window when you want to close it. But be aware, you may get a confirmation dialogbox of the window in question, and I think you don't want that...

Somewhere I must have an application wherein I displayed a list of a list of all open windows, giving the user the ability to choose one and click "end app". When I find the code I will post an excerpt here, ok?

Regards, Abel

Author

Commented:
Thanks, great.

Antony
Commented:
Unlock this solution with a free trial preview.
(No credit card required)
Get Preview

Commented:
Sorry about this if I'm taking your idea but I'll be writing a program that I'll give you if you want to disable the altering of certain, user-defined files because I like the idea and know how to go about it.
Congrats and write me at
recils@hotmail.com if you'd like a copy when I'm done

Commented:
Note, you can also use the CloseWindow function to close the window as it mearly requires the window's handle

Commented:
A good way to get around them finding it with ctrl-alt-del is to name it something inconspicuous.  Name it something like 32n58sDll not KILLSETUPS because obviously the second is more obvious.  Since ctrl-alt-del halts all programs when it executes you can't use CloseWindow to kill it.  Good luck figuring out a way :)
Unlock the solution to this question.
Thanks for using Experts Exchange.

Please provide your email to receive a free trial preview!

*This site is protected by reCAPTCHA and the Google Privacy Policy and Terms of Service apply.

OR

Please enter a first name

Please enter a last name

8+ characters (letters, numbers, and a symbol)

By clicking, you agree to the Terms of Use and Privacy Policy.