Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Need help writing a batch file to read a MS Access .ldb lock file with null delimiters

I am trying to create a batch file to read a Microsoft Access .ldb lock file. The lock file contains a list of computer names and user names. I want to extract the computer names and eventually run them against an external command.

The format of the batch file is a single row with (1) a computer name (2) a NULL character (Hex 00) (3) approximately 20 spaces (4) the user name (5) a NULL character (6) approximately 20 spaces repeating.

Example in Notepad++ with (NUL) representing Hex 00:

COMPUTER0123(NUL)                     Admin(NUL)                     COMPUTER0507(NUL)                     Admin(NUL)

I've tried several methods using FOR to read the file but can't get past the first computer name.

setlocal EnableDelayedExpansion
set file=database.ldb

for /F %%a in ('type %file%') do (
    echo %%a
    )

For for most of my Access databases, the user name in the file is Admin. I've been able to use FIND to tell me how many occurrences of "Admin" are in the file (plus 1).

for /f "delims=" %%n in ('find /c /v "Admin" %file%') do set "len=%%n"
set "len=!len:*:=!"
echo %len% (minus 1) computer names to process 
<%file% (
  for /l %%l in (1 1 !len!) do (  
    set "line="
    set /p "line="
    echo(!line!)    
    )
)

Iterating through the found lines doesn't work, probably because there only is one line in the file (no carriage returns).

I would like to find a solution that would work with a standard install of Windows XP.


After receiving an accepted answer, I combined that into a batch file that I'm posting below. I named the file ShowUsersInLDB.bat and put it in my SendTo folder.

@echo off
::===================================================================
:: Put this in your SendTo folder and it will let you right-click 
:: on an Access .ldb/.laccdb lock file and tell you the computer
:: names that have opened the database.  
::
:: After the computer names are shown, this will prompt you to 
:: search for the user names associated with each computer.  This
:: depends upon finding a 3rd party file named NetUsers.exe in
:: the user profile folder.  Feel free to change the path if you
:: want to store the file in another location.
:: 
:: NetUsers.exe can be downloaded from here:  http://www.optimumx.com/downloads.html#NetUsers
::
:: Notes:
:: 1) Keep in mind that sometimes after people leave the database 
:: the lock file still shows their computer name.  Don't jump
:: to conclusions.
:: 2) NetUsers.exe seems to report all users who have logged on
:: to the computer and not logged off, including services.  
:: If you aren't familiar with your user names or your users are
:: sharing remote desktops/Citrix/Terminal Services, you may have 
:: to guess who might have created the lock entry. 
::
:: Installation:
:: You may find a batch file named Install_UsersInLDB.bat that will 
:: copy this file to the SendTo folder and the NetUsers.exe file to 
:: the user profile (or a place you define).
::
:: Ben Sacherich - March 2014
:: Please let me know if you have any ideas for improvements.
::===================================================================

setlocal
set file="%1"

:: Make sure the file has a compatible extension.
if  "%~x1"==".ldb"    goto :ExtensionIsValid
if  "%~x1"==".laccdb" goto :ExtensionIsValid

echo.
echo "%~n1%~x1" is not the correct file type.
echo.
pause
goto :End

:ExtensionIsValid
echo The Access "%~n1%~x1" file contains
echo the following computer names:
echo.
set "compNameLine=1"
for /f %%A in ('more "%file%"') do (
  if defined compNameLine (
    echo %%A
    set "compNameLine="
  ) else set "compNameLine=1"
)

echo.
echo Are you ready to look up the user names on each computer?
pause

set "compNameLine=1"
for /f %%A in ('more "%file%"') do (
  if defined compNameLine (
    ::echo %%A
    "%userprofile%\netusers" \\%%A
    set "compNameLine="
  ) else set "compNameLine=1"
)

echo.
echo -- Validation finished at %time%  
pause
:End
exit
like image 884
Ben Avatar asked Oct 06 '22 16:10

Ben


1 Answers

CMD.EXE generally does not play nicely with NUL bytes. But there are a few external commands that can handle NUL bytes.

You also have to worry about the length of the "line". CMD.EXE does not like lines longer than 8191 bytes long.

I think your best bet is MORE since it converts NULs into new lines.

The following should echo your computer names.

@echo off
setlocal
set "file=database.ldb"
set "compNameLine=1"
for /f %%A in ('more "%file%"') do (
  if defined compNameLine (
    echo %%A
    set "compNameLine="
  ) else set "compNameLine=1"
)
like image 134
dbenham Avatar answered Oct 10 '22 01:10

dbenham