Sign in to follow this  
Followers 0
gspino

Search and replace all specific strings in a reg file

12 posts in this topic

I find myself in an emergency situation and I hope one of you can help ASAP. I have a reg file that was exported using a "REG EXPORT" dos command. This reg file is rather large (49K) and contains blank lines. I need to replace every instance of a particular string with another. I've tried a loop with StringReplace and it just doesn't seem to work and I can't figure out why. Perhaps it's bacause I need sleep, but I really could use some assistance fast. Please include sample code. This is what I have so far that doesn't work.

Thank you in advance. - Glen

RunWait("REG EXPORT " & '"HKEY_CURRENT_USER\Software\Microsoft\Windows NT\CurrentVersion\Windows Messaging Subsystem\Profiles"' & " p:\test.reg")

$file = FileOpen("p:\test.reg", 0)

If $file = -1 Then

Exit

EndIf

While 1

$line = FileReadLine($file)

StringReplace($line, "\\hfd-data-01", "\\hfddata02")

If @error = -1 Then ExitLoop

Wend

FileClose($file)

Share this post


Link to post
Share on other sites



#2 ·  Posted (edited)

I am not the best at this, and there are many better programmers out there besides me, but I am just trying to be helpful.

For starters, try:

1) deleting this :$line = FileReadLine($file)

2) making StringReplace($line, "\\hfd-data-01", "\\hfddata02") be this instead:

StringReplace($file, "\\hfd-data-01", "\\hfddata02")oÝ÷ Ø@ÈLßiËb!1È4¯âÊjx¶¸¡û(騭ë-¹÷í¢®¶­se'VåvBgV÷Cµ$TrUõ%BgV÷C²fײb33²gV÷C´´Uô5U%$TåEõU4U"b3#µ6ögGv&Rb3#´Ö7&÷6ögBb3#µvæF÷w2åBb3#´7W'&VçEfW'6öâb3#µvæF÷w2ÖW76vær7V'77FVÒb3#µ&öfÆW2gV÷C²b33²fײgV÷C²¢b3#·FW7Bç&VrgV÷C²¢b33c¶fÆRÒgV÷C·¢b3#·FW7Bç&VrgV÷C°¥7G&æu&WÆ6Rb33c¶fÆRÂgV÷C²b3#²b3#¶fBÖFFÓgV÷C²ÂgV÷C²b3#²b3#¶fFFF"gV÷C²¤fÆT6Æ÷6Rb33c¶fÆR
Edited by litlmike

Share this post


Link to post
Share on other sites

#3 ·  Posted (edited)

It makes no sense to handle this file line by line.

Example: A new line is only seperated by a single character. Just like a word is seperated by a space, also a single character.

Why would you do this line by line, and not word by word? I don't have a answer to that question. I would just do the whole file at once, and I bet it is faster too!

If you own beta:

$FileData = FileRead ("p:\test.reg")
$FileData = StringReplace($FileData, "\\hfd-data-01", "\\hfddata02")
FileWrite("p:\test.reg",$FileData)

If you don't, get it. It will save you a lot of trouble.

Edited by Manadar

Share this post


Link to post
Share on other sites

Why would you do this line by line, and not word by word? I don't have a answer to that question. I would just do the whole file at once, and I bet it is faster too!

There's times where the output isn't as desired as it is line by line.

[center]Common sense plays a role in the basics of understanding AutoIt... If you're lacking in that, do us all a favor, and step away from the computer.[/center]

Share this post


Link to post
Share on other sites

#5 ·  Posted (edited)

There's times where the output isn't as desired as it is line by line.

This would only be the case if the lines were seperated in for example a array. In that case, put a _ArrayToString on line 2 to counter this problem. In all other cases, when you have a string containing multiple lines, you could just do a StringReplace.. Correct me if i'm wrong.

I also see that the output in this particular question is a file. And a file can be read in multiple ways. So why not go with the easiest way?

Edited by Manadar

Share this post


Link to post
Share on other sites

This would only be the case if the lines were seperated in for example a array. In that case, put a _ArrayToString on line 2 to counter this problem. In all other cases, when you have a string containing multiple lines, you could just do a StringReplace.. Correct me if i'm wrong.

I also see that the output in this particular question is a file. And a file can be read in multiple ways. So why not go with the easiest way?

Well in this particular situation, I'm inclined to agree with you. But with as much string manipulation as I've been doing, StringReplace() just has too many limitations to be totally effective for me in all aspects of what I try to accomplish. I would think that StringRegExpReplace() would be a more suitable alternative, but as I've seen, not many understand the syntax and how to use it.

If you are wanting to replace something specific, case sensitivity isn't always the answer.

$String = "!a I want to replace only stand alone a (s)"
MsgBox(64, "info", StringReplace($String, "a", ""))
Unfortunately, this doesn't suit the needs of what my goal is, although it's very quick.

So in this case, we either go line by line (or as a whole if you know how to do it) and use a custom string function to do what you want, or use StringRegExpReplace().


[center]Common sense plays a role in the basics of understanding AutoIt... If you're lacking in that, do us all a favor, and step away from the computer.[/center]

Share this post


Link to post
Share on other sites

#include <file.au3>
#include <array.au3>

$file = " path to .reg file"
$codeVAL = _chkRegFile($file)
If $codeVAL = 105 Then
    Exit
ElseIf $codeVAL = 110 Then
    ;you have work to do, export as 9x format .reg file
    Exit
ElseIf $codeVAL = 115 Then
    ;sorry, no Big Endians
    Exit
EndIf
$fo = FileRead($file,0)
$ar = StringSplit($fo,"[")
For $x = 1 To UBound($ar) - 1
    If StringInStr($ar[$x],"seach string") Then $ar[$x] = StringReplace($ar[$x],"search string","replacement")
    ; make your filewriteline code here ie. FileWriteLine($handle,"[" & $ar[$x])
Next

Func _chkRegFile($checkF) ; check registry file for UTF type
    Local $tmpCHECK = FileOpen($checkF,4)
    If $tmpCHECK = -1 Then ; unable to open reg file
        Return 105
    EndIf
    Local $chkFILE = StringReplace(String(FileRead($tmpCHECK,FileGetSize($checkF))),"0x","")
    If StringMid($chkFILE,1,4) = "FFFE" Then
            MsgBox(4096,"Error","This registry file appears to be UTF-16 (Unicode)")
            Return 110
    ElseIf StringMid($chkFILE,1,4) = "FEFF" Then
            MsgBox(4096,"Error","This registry file is Big Endian Unicode.")
            Return 115
    EndIf
    FileClose($tmpCHECK)
    Return 0
EndFunc  ;--->>> _chkRegFile

late,

Sul

Share this post


Link to post
Share on other sites

Thank you all. I neglected to mention that the modified reg file needs to be imported back into the registry, so it's important that we don't change anything except for the string I need to replace. I will try some of your suggestions and I appreciate everyone's efforts.

Share this post


Link to post
Share on other sites

So far noe of the suggestions worked. I'm not sure if it's a unicode problem. It appears to be UTF-16 (native Windows XP reg export format). I'm at a loss, running out of time and very tired. Thank you all for trying. If you think of any new ideas, please let me know. I'm sure I'll wake up during the night worrying over this. -Glen

Share this post


Link to post
Share on other sites

So far noe of the suggestions worked. I'm not sure if it's a unicode problem. It appears to be UTF-16 (native Windows XP reg export format).

Easy way to tell. Open the reg file in a hex editor and you will see format like this 72,00,34,00,22,00,54,00,3e,00 for Unicode, whereas ascii will be 72,34,22,54,3e etc. You could also open it, and then click Save As and save it as Ascii/ANSI. Windows will tell you that if you do this you will lose encoding features and such.

I have been working with lot's and lot's of reg files in the last month or so. What you want Autoit to do is most definately possible. I have been converting reg files to inf structures which are some in the range of 400-500k. But I initially had a problem with the unicode formatting.

Dump it to 9x reg file unless you have extended characters. Then all the normal string functions should operate just fine.

Sul

Share this post


Link to post
Share on other sites

#12 ·  Posted (edited)

Easy way to tell. Open the reg file in a hex editor and you will see format like this 72,00,34,00,22,00,54,00,3e,00 for Unicode, whereas ascii will be 72,34,22,54,3e etc. .......

Sul

Thank you all. I've got it worked out. I took suggestions from everyone and put together a solution that works. It may look a little clunky, but the conversion from unicode to ascii was the big nut. It turns out that if you use the DOS TYPE command and redirect the output to another file, it is automatically converted from unicode to ascii. The rest was easy. I pasted the source below in case anyone could use it.

Just for reference, this issue was that roaming and user profiles were moved to another server. The references in the users reg hive had unc pointers to their networkt PST files that needed to be changed. There is no tool that does this process in Exchange 2000. Microsoft would not help since they still don't support pst issues unless they are stored locally. I couldn't perform any string functions because the REG EXPORT command in XP automatically saves it's output in Unidode-16.

;==============================================

;PSTFIX.AU3

;GSPINO 10.09.2006

;USE AUTOIT TO COMPILE

;REG FILE EXPORT FILE IS IN UNICODE-16

;YOU CANNOT PERFORM STRING FUNCTIONS ON UNICODE CHARACTORS

;THE FILECOPY STEPS CONVERT UNICODE-16 TO ASCII

;==============================================

;PREVENT MULTIPLE INSTANCES FROM RUNNING SIMULTANEOUSLY

$g_szVersion = "pstfix"

If WinExists($g_szVersion) Then Exit

AutoItWinSetTitle($g_szVersion)

;==============================================

;EXIT IF FLAG FILE IS PRESENT

If Not FileExists("c:\pstfix.flg") Then

;EXPORT THE REGISTRY KEY THAT CONTAINS THE REFERENCES TO HFD-DATA-01

RunWait("REG EXPORT " & '"HKEY_CURRENT_USER\Software\Microsoft\Windows NT\CurrentVersion\Windows Messaging Subsystem\Profiles"' & " c:\pstfixu.reg")

;MAKE A TEXT COPY

FileCopy("c:\pstfixu.reg", "c:\pstfixu.txt", 1)

;CONVERT FROM UNICODE-16 TO ASCII

RunWait(@ComSpec & " /c " & "TYPE c:\pstfixu.txt > c:\pstfixa.txt", "", @SW_HIDE)

;PERFORM SEARCH & REPLACE OF ALL INSTANCES OF HFD-DATA-01 WITH HFDDATA02

$FileIn = FileOpen("c:\pstfixa.txt", 0)

$FileOut = FileOpen("c:\pstfix.txt", 2)

While 1

$linein = FileReadLine($FileIn)

If @error = -1 Then ExitLoop

$lineout = StringReplace($linein, "hfd-data-01", "hfddata02")

FileWriteLine($FileOut, $lineout)

WEnd

FileClose($FileIn)

FileClose($FileOut)

;COPY THE TXT FILE TO A REGFILE

FileCopy("c:\pstfix.txt", "c:\pstfix.reg", 1)

;IMPORT THE REGFILE

RunWait(@ComSpec & " /c " & "REG IMPORT" & " c:\pstfix.reg", "", @SW_HIDE)

;==============================================

;CLEANUP - DELETE ASSOCIATED FILES

FileDelete("c:\pst*.reg")

FileDelete("c:\pst*.txt")

;INSERT FLAG FILE

RunWait(@ComSpec & " /c " & "echo.>> c:\pstfix.flg", "", @SW_HIDE)

;DISPLAY MESSAGE TO THE USER AND LOG OFF THE USER IN 10 SECONDS

MsgBox(0, "Notice", "Your email settings have been changed. " & @CRLF & " You will be logged off in 10 seconds or click OK to log of now." & @CRLF & " You may log right back in immediately." & @CRLF & " Thank you. I.S. Staff", 10)

Shutdown(0)

Exit

EndIf

;==============================================

Exit

Edited by gspino

Share this post


Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!


Register a new account

Sign in

Already have an account? Sign in here.


Sign In Now
Sign in to follow this  
Followers 0