Jump to content

FileRead works on Autorun.inf while Ini functions sometimes don't

Recommended Posts

I've made a program that relies on IniReadSectionNames. It reads (~3K) Autorun.inf files in the working folder and creates a GUI based on their contents.

I made sure to revert to a default GUI upon @error.

But someone (with Windows XP SP3 32-bit) reported to me he always gets the default menu.

I sent him a FileRead command instead and it works! So seemingly there's no access problem to AutoRun.inf.

In the following demo code, I always hit success, but he always ends up with semi-success:

Local $hIniLocation = "Autorun.inf"
    Local $aSections = IniReadSectionNames($hIniLocation)
    If @error Then
        $aSections = FileRead($hIniLocation)
        if @error then
            msgbox(48, "Double error", "Alternative access failed too due to:" & @crlf & @error & @crlf & @extended)
            msgbox(0, "Semi-success", "IniReadSectionNames failed, but alternativaly this file contains:" & @crlf & @crlf & $aSections)
        msgbox(0, "Success", "IniReadSectionNames worked!")

Why is that? Is there something further to check with him?


Edited by LWC
More general topic and tag
Link to post
Share on other sites

It seems to be about Autorun.inf specifically. If I change my script to use autorun.ini or something_else.inf, then it works for him.

But if FileRead works on Autorun.inf itself, why doesn't IniReadSectionNames?

Can I check the relevant rights and/or pipe IniReadSectionNames through FileRead (without creating a temp file just so it won't be called Autorun.inf)?

Edited by LWC
Link to post
Share on other sites

Checking the rights for this particular file on one particular PC could be not easy if trouble comes from antivirus policy etc
But if FileRead works you might provide an alternative way as a workaround

#include <Array.au3>
$txt = FileRead(@ScriptDir & "\Autorun.inf")
$sections = StringRegExp($txt, '^|(?m)^\s*\[([^\]]+)', 3)
$sections[0] = UBound($sections)-1


Link to post
Share on other sites

That's very smart and works perfectly, thanks!

I'll submit a bug report asking to use your code internally in IniReadSectionNames as a fallback (unless of course they'll fix it directly).

But...IniReadSection suffers from the same issue. Can you suggest a bypass for it too?

Edited by LWC
Link to post
Share on other sites
1 hour ago, LWC said:

I'll submit a bug report

IMHO it's not a good idea as the problem certainly comes from some particular configuration on the user's PC
Workarounds exist for most Ini* funcs. How many of these funcs is your script using ?

Link to post
Share on other sites

I assume that File/Ini funcs don't all work the same way. Question for developpers  :)

Here is a possible workaround for IniReadSection

#include <Array.au3>

$txt = FileRead(@ScriptDir & "\Autorun.inf")
$sections = StringRegExp($txt, '^|(?m)^\s*\[([^\]]+)', 3)
$sections[0] = UBound($sections)-1

For $i = 1 To $sections[0]
   ; read content of section
   $content = StringRegExp($txt, '\Q' & $sections[$i] & ']\E\s+([^\[]+)', 1)
   If IsArray($content) Then 
       ; get key/value pairs
       $tmp = StringRegExp($content[0], '(?m)^([^\v;=]+)=([^;\v]*)\N*$', 3)
       If not IsArray($tmp) Then 
            Msgbox(0,"", "section " & $sections[$i] & " is empty")
       ; format to 2D array
       $n = UBound($tmp)
       Local $aArray[$n/2+1][2]
       For $j = 0 To $n-1
            $aArray[Int($j/2)+1][Mod($j, 2)] = $tmp[$j]
       $aArray[0][0] = $n/2
      _ArrayDisplay($aArray, "section " & $sections[$i])
      Msgbox(0,"", "section " & $sections[$i] & " is empty")


Edited by mikell
Link to post
Share on other sites

I used your first regexp, but then continued with some simpler code combined with ideas from here.

#include <Array.au3>

$txt = FileRead(@ScriptDir & "\Autorun.inf")
$aSections = StringRegExp($txt, '^|(?m)^\s*\[([^\]]+)', 3)
$aSections[0] = UBound($aSections)-1

    For $iCount = 1 To $aSections[0]
        if $filecontent="" then
            $aKV = IniReadSection($hIniLocation, $aSections[$iCount])
            If @error Then ; If empty section then ignore (treat as void)
            $value = StringRegExp($filecontent, "\Q" & $aSections[$iCount] & ']\E\s+([^\[]+)', 1)
            If not IsArray($value) Then ; If empty section then ignore (treat as void)
            If StringInStr($value[0], @CRLF, 1, 1) Then
                $value = StringSplit(StringStripCR($value[0]), @LF)
            ElseIf StringInStr($value[0], @LF, 1, 1) Then
                $value = StringSplit($value[0], @LF)
                $value = StringSplit($value[0], @CR)
            local $aKV[1][2]
            For $xCount = 1 To $value[0]
                if $value[$xCount]="" or StringLeft($value[$xCount], 1)=";" then ContinueLoop
                ReDim $aKV[ubound($aKV)+1][ubound($aKV, 2)]
                $value_temp = StringSplit($value[$xCount], "=", 2)
                $aKV[ubound($aKV)-1][0] = $value_temp[0]
                $aKV[ubound($aKV)-1][1] = $value_temp[1]
                $aKV[0][0] += 1
            if $aKV[0][0]="" then ContinueLoop
        _ArrayDisplay($aKV, $aSections[$iCount])

What do you think?

Edited by LWC
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
  • Recently Browsing   0 members

    No registered users viewing this page.

  • Similar Content

    • By AspirinJunkie
      I've noticed that for the task of "reading a file row by row into an array" FileReadToArray is consistently slower than a FileRead + StringSplit.
      The following script:
      Results in the following output for me:
      And the output with switched call sequence:
      This surprises me, since I first assume that the native function offers more optimization possibilities than having to create an array in AutoIt via an intermediate string.
      So I thought that maybe FileReadToArray is more economical with memory. But again FileReadToArray seems to consume more memory than the StringSplit variant. For this I got the PeakWorkingSetSize after the call of the respective function.
      After FileReadToArray the Size is always higher than with StringSplit. Since this is not the case if one changes the order of the two functions (see above), one can assume that FileReadToArray actually has this difference. The difference is mostly the double file size. Which would make sense if the file is completely saved internally as a UTF-16 string.
      Can anyone explain to me why FileReadToArray performs so unexpectedly poor - or am I missing something?
    • By nacerbaaziz
      good morning sirs.
      please i have a request from you.
      i have an variable to Read a data from a file
      this data is Encrypted
      and when i read it i Decrypte it.
      for that i need a function to Write a ini data to string.
      ;#Function# ===================================================================================================================== ; Name............: _IniReadFromString ; Description.....: Returns the value of a key in a specific section of an ini-formatted string ; Syntax..........: _IniReadFromString($szInput, $szSection, $szKey, $Default) ; Parameters......: ;   $szInput - The string that contains data in ini format ;   $szSection   - The sectionname (just as in IniRead) ;   $szKey   - The keyname (just as in IniRead) ;   $Default - The default value if the key does not exist or reading failed (just as in IniRead) ; Return values ..: ;   Success  - Returns the read value ;   Failure  - Returns $Default ; Author .........: FichteFoll ; Remarks ........: Works for Unicode as well as for ANSI ; Related ........: IniRead, _IniReadSectionFromString ; Link ...........; See on top ; Example ........; $var = _IniReadFromString(StringFormat("[Sect]\r\nMyKey1=value1\r\nMyKey2=value2"), "Sect", "MyKey2", "no_value") ; =============================================================================================================================== Func _IniReadFromString($szInput, $szSection, $szKey, $Default) $szInput = StringStripCR($szInput) ;~  Local $aRegMl = StringRegExp($szInput, "\[" & __StringEscapeRegExp($szSection) & "\]\n+(?:[^\[].*?=.*\n)*" & __StringEscapeRegExp($szKey) & "=(.*)\n?(",3) Local $aRegMl = StringRegExp($szInput, "\[" & __StringEscapeRegExp($szSection) & "\]\n+(?:[^\[].*?=.*\n)*" & __StringEscapeRegExp($szKey) & "=(.*)\n?", 3) If @error Then Return SetError(1, 0, $Default) ; key not found    Return $aRegMl[0] EndFunc;==>_IniReadFromString ; ############################################################################################################################### ; =============================================== ; = Internal Use Only ; =============================================== Func __StringEscapeRegExp($szExp) Return StringRegExpReplace($szExp, "([\(\)\[\]\{\}\\\/\?\.\\|\+])", "\\$1") ; ()[]{}\/?.|+ EndFunc;==>__StringEscapeRegExp like this  function Read the ini from string.
      please ihelp me
      thanks in advance
    • By Clark
      Hello all
      A programme I wrote for the organisation for which I work has been in use for a number of years with no issue.  One of the things that it does is allow for attachments to be selected (Word docs, Excel sheets, etc) which it then writes away as a BLOB in MySQL.
      This was all working fine until recently, when suddenly, on the odd occasion, Word would advise that the file was corrupt on retrieval of the BLOB from MySQL.
      Upon further examination it appears that the issue is not with the retrieval of the data from MySQL, but reading in the data from the disk by AutoIT.   It seems that on occasions that AutoIT will only read half the file.  
      I have no idea why this is, as the whole function is very simple.   I have included a sanitised vesion of it below in the hope that someone can tell me where to look next, as this one has me beat (again).  😋
      I have put some comments in to show what I have done to try and solve the problem, but am getting no closer to the truth.  @error is the strangest one - it should return -1 when it reaches end of file but is returning zero. 
      Func _AttachAttachment() local $file,$chars,$fsize If $RFC_Retrieved = False Then msgbox(0,"Error","Must have a RFC active first") Else $file=FileOpenDialog("Attach to RFC",".","All (*.*)",1) ; Check if file opened for reading OK If $file = -1 Then MsgBox(0, "Error", "Unable to open file.") Exit EndIf ; FileClose($file) These two lines are my attempt to open the file in binary mode. Made no difference ; FileOpen($file,16) ; Read in the File $fsize = FileGetSize($file) ConsoleWrite("File size is " & $fsize & @CRLF) ; the size comes back as what it say in Windows properties ; $chars = FileRead($file,$fsize) ; I was using this, then tried the line following this. It didn't help $chars = FileRead($file) ; This is showing a figure $chars/2 - 1 I don't understand this ConsoleWrite("Number of chars read is " & @extended & " error code is " & @error & @crlf) ; @error is coming back with 0. I don't understand this as I thought it would be -1 FileClose($file) EndIf EndIf EndFunc Thanks in advance for looking at this
    • By nacerbaaziz
      hello sirs,
      i have searched allot about an function that can  read the INI file as a  string
      i mean function to read the ini files from string and not from the file directly.
      i finally found an UDF that do what i want
      but unfortunately all the functions work,  but the function that i want it not working.
      this is the udf
      the function that  i need is _IniReadFromString
      this is the function

      Func _IniReadFromString($szInput, $szSection, $szKey, $Default) $szInput = StringStripCR($szInput) Local $aRegMl = StringRegExp($szInput, "\[" & __StringEscapeRegExp($szSection) & "\]\n+(?:[^\[].*?=.*\n)*" & __StringEscapeRegExp($szKey) & "=(.*)\n?(", 3) If @error Then Return SetError(1, 0, $Default) ; key not found Return $aRegMl[0] EndFunc;==>_IniReadFromString
      i hope that any one can help me
      thank you in advance
    • By nacerbaaziz
      hi dears
      am using an ini files as a History
      Sometimes the file size is be larger to 5 MB
      AutoIt does not recognize the full content of the file
      When I did a search to find out why, I discovered that INI files could not be read if they size larger than 64 KB.
      for that I preferred to ask here if is there any way to bypass this obstacle.
      The contents of the file are  as follows
      ....... Etc
      This is the section for reading the file (adapted from my main script)

      case $continue     Local $aArray = IniReadSection($WaitingListFile, StringEncrypt(true, "filesList", $MyPassword))     If Not @error Then Opt("GUICloseOnESC", 1) _GUICtrlListView_DeleteAllItems($scList)         For $i = 1 To $aArray[0][0] $path = path_list(StringEncrypt(false, $aArray[$i][0], $MyPassWord), 1) if FileExists(StringEncrypt(false, $aArray[$i][0], $MyPassWord)) then GUICtrlCreateListViewItem(_GetFileName(FileGetLongName(StringEncrypt(false, $aArray[$i][0], $MyPassWord))) & Opt("GUIDataSeparatorChar") & " : " & Opt("GUIDataSeparatorChar") & FileGetLongName(StringEncrypt(false, $aArray[$i][0], $MyPassWord)), $scList) else $path = $path endIf         Next GUISetState(@sw_disable, $hGUI) GUISetState(@sw_show, $hGUI2) GUICtrlSetState($SClist, $GUI_FOCUS) else if $accessibilitymode = 1 then speak(str("listEmpty")) endIf endIf
      Is there any way to solve this problem, please?
      am waiting your answers...
      Greetings to All
  • Create New...